Skip to main content

Configurar la reutilización de conexiones para el SDK de DashScope

Sin la reutilización de conexiones, cada llamada a la API abre una nueva conexión TCP y realiza un protocolo de enlace TLS, lo que añade latencia. En escenarios de alta concurrencia, esta sobrecarga provoca tiempos de espera y desperdicio de recursos. La reutilización de conexiones elimina la configuración repetida, reduciendo la latencia y el consumo de recursos.

El SDK de DashScope admite la reutilización de conexiones tanto en Java como en Python:
  • SDK de Java: Un grupo de conexiones integrado está habilitado de forma predeterminada. Configure parámetros como el máximo de conexiones y los tiempos de espera.
  • SDK de Python: Habilite la reutilización de conexiones pasando un cliente HTTP personalizado. Admite llamadas síncronas y asíncronas.

Antes de comenzar

Antes de ejecutar los ejemplos de código:
  1. Exporte la clave de API como variable de entorno.
  2. Instale el SDK más reciente.

SDK de Java

El SDK de Java incluye un grupo de conexiones integrado habilitado de forma predeterminada. Ajuste las configuraciones de conexiones máximas y tiempos de espera para optimizar su carga de trabajo.

Parámetros

ParámetroDescripciónValor predeterminadoUnidad
connectTimeoutTiempo de espera de establecimiento de conexión.120segundos
readTimeoutTiempo de espera de lectura de datos.300segundos
writeTimeoutTiempo de espera de escritura de datos.60segundos
connectionIdleTimeoutTiempo de espera de conexión inactiva en el pool.300segundos
connectionPoolSizeNúmero máximo de conexiones en el pool.32conexiones
maximumAsyncRequestsNúmero máximo de solicitudes simultáneas en todos los hosts (límite global).32solicitudes
maximumAsyncRequestsPerHostNúmero máximo de solicitudes simultáneas por host.32solicitudes
Restricciones de parámetros:
  • maximumAsyncRequests debe ser ≤ connectionPoolSize; de lo contrario, las solicitudes podrían bloquearse.
  • maximumAsyncRequestsPerHost debe ser ≤ maximumAsyncRequests.
Directrices de ajuste:
  • connectTimeout: En escenarios de baja latencia, establezca un tiempo de espera más corto para reducir el tiempo de espera.
  • connectionIdleTimeout: En escenarios de alta concurrencia, extienda el tiempo de espera de inactividad para evitar la creación frecuente de conexiones y reducir el consumo de recursos.
  • connectionPoolSize: En escenarios de alta concurrencia, muy pocas conexiones causan bloqueos, tiempos de espera y reconexiones frecuentes (mayor uso de recursos). Demasiadas conexiones sobrecargan el servidor. Equilibre el recuento de conexiones según su carga de trabajo.

Ejemplo de código

El siguiente ejemplo configura los parámetros del grupo de conexiones (tiempo de espera, conexiones máximas) y llama a un servicio de modelo. Ajuste los parámetros para optimizar la concurrencia y el uso de recursos.
// Recommended DashScope SDK version >= 2.12.0
import java.time.Duration;
import java.util.Arrays;

import com.alibaba.dashscope.aigc.generation.Generation;
import com.alibaba.dashscope.aigc.generation.GenerationParam;
import com.alibaba.dashscope.aigc.generation.GenerationResult;
import com.alibaba.dashscope.common.Message;
import com.alibaba.dashscope.common.Role;
import com.alibaba.dashscope.exception.ApiException;
import com.alibaba.dashscope.exception.InputRequiredException;
import com.alibaba.dashscope.exception.NoApiKeyException;
import com.alibaba.dashscope.protocol.ConnectionConfigurations;
import com.alibaba.dashscope.protocol.Protocol;
import com.alibaba.dashscope.utils.Constants;

public class Main {
    public static GenerationResult callWithMessage() throws ApiException, NoApiKeyException, InputRequiredException {
        // This is the Singapore region URL. Replace WorkspaceId with your actual workspace ID. URLs differ by region.
        Generation gen = new Generation(Protocol.HTTP.getValue(), "https://{WorkspaceId}.ap-southeast-1.maas.aliyuncs.com/api/v1");
        Message systemMsg = Message.builder()
                .role(Role.SYSTEM.getValue())
                .content("You are a helpful assistant.")
                .build();
        Message userMsg = Message.builder()
                .role(Role.USER.getValue())
                .content("Who are you?")
                .build();
        GenerationParam param = GenerationParam.builder()
                // API keys for Singapore and Beijing regions differ. Get an API key: https://www.alibabacloud.com/help/model-studio/get-api-key
                // If you have not configured the environment variable, replace the following line with your Model Studio API key: .apiKey("sk-xxx")
                .apiKey(System.getenv("DASHSCOPE_API_KEY"))
                // This example uses qwen-plus. Change the model name as needed. Model list: https://www.alibabacloud.com/help/model-studio/getting-started/models
                .model("qwen-plus")
                .messages(Arrays.asList(systemMsg, userMsg))
                .resultFormat(GenerationParam.ResultFormat.MESSAGE)
                .build();

        System.out.println(userMsg.getContent());
        return gen.call(param);
    }
    public static void main(String[] args) {
        // Connection pool configuration
        Constants.connectionConfigurations = ConnectionConfigurations.builder()
                .connectTimeout(Duration.ofSeconds(10))  // Timeout for establishing a connection, default 120s
                .readTimeout(Duration.ofSeconds(300)) // Timeout for reading data, default 300s
                .writeTimeout(Duration.ofSeconds(60)) // Timeout for writing data, default 60s
                .connectionIdleTimeout(Duration.ofSeconds(300)) // Timeout for idle connections in the connection pool, default 300s
                .connectionPoolSize(256) // Maximum connections in the connection pool, default 32
                .maximumAsyncRequests(256)  // Maximum concurrent requests, default 32
                .maximumAsyncRequestsPerHost(256) // Maximum concurrent requests per host, default 32
                .build();

        try {
            GenerationResult result = callWithMessage();
            System.out.println(result.getOutput().getChoices().get(0).getMessage().getContent());
        } catch (ApiException | NoApiKeyException | InputRequiredException e) {
            // Use a logging framework to record exception information
            System.err.println("An error occurred while calling the generation service: " + e.getMessage());
        }
        System.exit(0);
    }
}

SDK de Python

El SDK de Python admite la reutilización de conexiones al pasar un cliente HTTP personalizado (httpx.Client / httpx.AsyncClient). Admite dos métodos de llamada: HTTP asíncrono (basado en corrutinas) y HTTP síncrono.

HTTP asíncrono

Para escenarios asíncronos, use httpx.AsyncClient junto con httpx.Limits para habilitar la reutilización de conexiones. httpx.Limits admite la configuración de parámetros como límites de conexiones:
ParámetroDescripciónValor predeterminadoNotas
max_connectionsLímite total de conexiones.None (ilimitado)Controla el número máximo de conexiones. En escenarios de alta concurrencia, aumente este valor para mejorar la concurrencia.
max_keepalive_connectionsNúmero máximo de conexiones keep-alive.None (ilimitado)Controla el número de conexiones activas que se mantienen en el grupo, evitando una carga excesiva en un solo servidor.
keepalive_expiryTiempo de espera keep-alive de las conexiones.5.0 (segundos)Las conexiones keep-alive inactivas se cierran automáticamente transcurrida esta duración.

Ejemplo de código

El siguiente ejemplo configura la reutilización de conexiones y llama a un servicio de modelo de forma asíncrona:
import asyncio
import httpx
import os
import dashscope

async def main():
    # Configure los parámetros de conexión
    limits = httpx.Limits(
        max_connections=100,           # Límite total de conexiones
        max_keepalive_connections=30,  # Número máximo de conexiones keep-alive
    )

    # Cree un cliente HTTP personalizado y páselo al constructor de Client
    async with httpx.AsyncClient(limits=limits) as http_client:
        # La siguiente es la configuración de la región de Singapur. Sustituya {WorkspaceId} por el ID real de su espacio de trabajo. El valor de region varía según la región.
        # La API Key de la región de Singapur es diferente de la de la región de Pekín. Obtenga una API Key: https://www.alibabacloud.com/help/model-studio/get-api-key
        # Si no se ha configurado la variable de entorno, establezca su API key directamente: api_key = "sk-xxx"
        aclient = dashscope.AsyncClient(
            api_key=os.getenv("DASHSCOPE_API_KEY"),
            workspace="{WorkspaceId}",
            region="ap-southeast-1",
            http_client=http_client,  # Pase el cliente HTTP personalizado
        )
        response = await aclient.chat.completions.create(
            model='qwen-plus',
            messages=[{"role": "user", "content": 'Hello, please introduce yourself'}],
        )
        print(response)

asyncio.run(main())

HTTP síncrono

Para escenarios síncronos, use httpx.Client para habilitar la reutilización de conexiones. Múltiples solicitudes dentro del mismo cliente HTTP reutilizan la conexión TCP subyacente, evitando la sobrecarga de establecer conexiones repetidamente.

Ejemplo de código: llamada única

El siguiente ejemplo configura la reutilización de conexiones y llama a un servicio de modelo de forma síncrona:
import httpx
import os
import dashscope

# Use la sentencia with para asegurar el cierre correcto del cliente HTTP
with httpx.Client() as http_client:
    # La siguiente es la configuración de la región de Singapur. Sustituya {WorkspaceId} por el ID real de su espacio de trabajo. El valor de region varía según la región.
    # La API Key de la región de Singapur es diferente de la de la región de Pekín. Obtenga una API Key: https://www.alibabacloud.com/help/model-studio/get-api-key
    # Si no se ha configurado la variable de entorno, establezca su API key directamente: api_key = "sk-xxx"
    client = dashscope.Client(
        api_key=os.getenv("DASHSCOPE_API_KEY"),
        workspace="{WorkspaceId}",
        region="ap-southeast-1",
        http_client=http_client,  # Pase el cliente HTTP personalizado
    )
    response = client.chat.completions.create(
        model='qwen-plus',
        messages=[{"role": "user", "content": 'Hello'}],
    )
    print(response)

Ejemplo de código: múltiples llamadas con un cliente HTTP compartido

Para reutilizar un cliente HTTP en múltiples llamadas:
import httpx
import os
import dashscope

# Cree un objeto de cliente HTTP y configure los parámetros de reutilización de conexiones
http_client = httpx.Client(
    limits=httpx.Limits(
        max_connections=100,          # Límite total de conexiones
        max_keepalive_connections=30, # Número máximo de conexiones keep-alive
    ),
)

# La siguiente es la configuración de la región de Singapur. Sustituya {WorkspaceId} por el ID real de su espacio de trabajo. El valor de region varía según la región.
# La API Key de la región de Singapur es diferente de la de la región de Pekín. Obtenga una API Key: https://www.alibabacloud.com/help/model-studio/get-api-key
# Si no se ha configurado la variable de entorno, establezca su API key directamente: api_key = "sk-xxx"
client = dashscope.Client(
    api_key=os.getenv("DASHSCOPE_API_KEY"),
    workspace="{WorkspaceId}",
    region="ap-southeast-1",
    http_client=http_client,  # Pase el cliente HTTP personalizado
)

try:
    # Reutilice el mismo cliente HTTP en múltiples llamadas
    response1 = client.chat.completions.create(
        model='qwen-plus',
        messages=[{"role": "user", "content": 'Hello'}],
    )
    print(response1)

    response2 = client.chat.completions.create(
        model='qwen-plus',
        messages=[{"role": "user", "content": 'Introduce yourself'}],
    )
    print(response2)
finally:
    # Asegure el cierre correcto del cliente HTTP
    http_client.close()

Mejores prácticas

  • SDK de Java: Establezca connectionPoolSize y maximumAsyncRequests según su carga de trabajo. Equilibre el recuento de conexiones: muy pocas causan bloqueos, demasiadas sobrecargan el servidor.
  • SDK de Python: Utilice la sentencia with para gestionar automáticamente el ciclo de vida del cliente HTTP y garantizar la limpieza correcta de recursos.
  • Elija el método adecuado: Use llamadas asíncronas para aplicaciones asíncronas (asyncio, FastAPI). Use llamadas síncronas para aplicaciones síncronas tradicionales.

Códigos de error

Si una llamada al modelo falla (el SDK de Python lanza una excepción DashScopeError y las llamadas HTTP devuelven un mensaje de error), consulte Mensajes de error para resolver el problema.