Inicio rápido de la API de Kimi K3: Python, streaming, visión y herramientas

Aprende a usar la API de Kimi K3 con Python y cURL, incluido el esfuerzo de razonamiento, streaming, visión, salida estructurada, herramientas y los límites del contexto de 1M.

Kimi K3 es el modelo insignia de Kimi para programación, trabajo de conocimiento y escenarios de razonamiento complejos. Utiliza Kimi Delta Attention (KDA), Attention Residuals y arquitectura MoE, tiene una escala de parámetros de 2,8 billones y proporciona comprensión visual nativa y 1 millón de contexto de token.

Este artículo se basa enKimi K3 官方 Quickstart, comienza con la clave API y las llamadas mínimas, clasifica ejemplos ejecutables de Python, cURL, salida de streaming, entrada visual, salida estructurada y llamadas a herramientas, y marca las diferencias de parámetros que se encuentran más fácilmente al migrar desde K2.x.

Quick Answer

Prepare Python 3.9+ y la clave API de Kimi, instale el SDK de OpenAI, escriba la clave enMOONSHOT_API_KEY, luego apunte elbase_urldel cliente OpenAI ahttps://api.moonshot.ai/v1y usekimi-k3para el nombre del modelo.

1
python3 -m pip install --upgrade 'openai>=1.0'
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
import os

from openai import OpenAI

client = OpenAI(
    api_key=os.environ["MOONSHOT_API_KEY"],
    base_url="https://api.moonshot.ai/v1",
)

completion = client.chat.completions.create(
    model="kimi-k3",
    messages=[{"role": "user", "content": "用一句话介绍 Kimi K3。"}],
)

print(completion.choices[0].message.content)

K3 siempre está en modo de pensar. Para establecer explícitamente la intensidad de la inferencia, utilice el campo de nivel superiorreasoning_effort="max"y no herede el parámetrothinkingde K2.x.

Preparar clave API y variables de entorno

Primero obtenga la clave API de Kimi API Platform. No escriba la clave directamente en el script ni la envíe a Git. Se recomienda pasarlo a través de variables de entorno.

Windows PowerShell

1
2
$env:MOONSHOT_API_KEY = "你的 API Key"
python .\kimi_k3_demo.py

Para guardar permanentemente para el usuario actual de Windows, ejecute:

1
[Environment]::SetEnvironmentVariable("MOONSHOT_API_KEY", "你的 API Key", "User")

Vuelva a abrir la terminal después de guardar.

macOS y Linux

1
2
export MOONSHOT_API_KEY="你的 API Key"
python3 kimi_k3_demo.py

Utilice cURL para completar la llamada mínima

Si no desea crear un proyecto de Python primero, puede llamar directamente a la interfaz compatible con OpenAI Chat Completions:

1
2
3
4
5
6
7
curl https://api.moonshot.ai/v1/chat/completions \
  --header "Authorization: Bearer $MOONSHOT_API_KEY" \
  --header "Content-Type: application/json" \
  --data '{
    "model": "kimi-k3",
    "messages": [{"role": "user", "content": "用一句话介绍 Kimi K3。"}]
  }'

Invoke-RestMethodse puede usar en PowerShell para evitar copiar directamente los saltos de línea de barra invertida de Bash:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
$headers = @{
    Authorization = "Bearer $env:MOONSHOT_API_KEY"
    "Content-Type" = "application/json"
}

$body = @{
    model = "kimi-k3"
    messages = @(
        @{ role = "user"; content = "用一句话介绍 Kimi K3。" }
    )
} | ConvertTo-Json -Depth 5

Invoke-RestMethod `
    -Uri "https://api.moonshot.ai/v1/chat/completions" `
    -Method Post `
    -Headers $headers `
    -Body $body

Establecer la fuerza de inferencia de K3

Actualmente, K3 solo admitemax, que también es el valor predeterminado. El funcionario agregará más marchas en el futuro, por lo que este campo puede omitirse en esta etapa; si quieres que la intención de configuración sea más clara, puedes escribir así:

1
2
3
4
5
6
7
8
9
completion = client.chat.completions.create(
    model="kimi-k3",
    reasoning_effort="max",
    messages=[
        {"role": "user", "content": "证明根号 2 是无理数。"}
    ],
)

print(completion.choices[0].message.content)

En múltiples rondas de conversaciones y llamadas a herramientas, el mensaje completo del asistente devuelto por la API debe volver a colocarse en la siguiente solicitud. No puedes quedarte solo concontent. El mensaje completo también puede contener información necesaria para la inferencia y la invocación de herramientas, lo que puede conducir fácilmente a un contexto incompleto después de la poda.

Manejar el razonamiento de transmisión y la respuesta final por separado

Una respuesta en tiempo real ubicaría el proceso de pensamiento enreasoning_contenty la respuesta final encontent. La interfaz de la aplicación puede manejar dos tipos de incrementos por separado:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
stream = client.chat.completions.create(
    model="kimi-k3",
    messages=[{"role": "user", "content": "解释天空为什么是蓝色的。"}],
    stream=True,
)

for chunk in stream:
    delta = chunk.choices[0].delta
    reasoning = getattr(delta, "reasoning_content", None)
    if reasoning:
        print(reasoning, end="", flush=True)
    if delta.content:
        print(delta.content, end="", flush=True)

Los entornos de producción normalmente deben almacenar o mostrarreasoning_contentpor separado de la respuesta final a los usuarios para evitar que la interfaz confunda las dos partes del contenido.

Enviar fotos locales

Elcontentdel mensaje visual debe ser una matriz de objetos y la matriz no se puede serializar en una cadena. K3 no admite la lectura directa de URL de imágenes públicas. Las imágenes locales deben convertirse a la URL de datos Base64:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
import base64
from pathlib import Path

image_data = base64.b64encode(Path("image.png").read_bytes()).decode()

completion = client.chat.completions.create(
    model="kimi-k3",
    messages=[
        {
            "role": "user",
            "content": [
                {
                    "type": "image_url",
                    "image_url": {
                        "url": f"data:image/png;base64,{image_data}"
                    },
                },
                {"type": "text", "text": "描述这张图片。"},
            ],
        }
    ],
)

print(completion.choices[0].message.content)

El vídeo debe cargarse primero a través de la API de Archivos y luego hacer referencia a él conms://<file-id>; recuerde eliminar los archivos temporales una vez completada la tarea para evitar retener datos inútiles durante mucho tiempo.

Utilice una salida de esquema JSON estricta

Cuando es necesario entregar los resultados al programa para su procesamiento de manera estable, el resultado final puede limitarse ajson_schemaystrict: true. Al analizar, lea solomessage.contenty no analicereasoning_content.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
import json

completion = client.chat.completions.create(
    model="kimi-k3",
    messages=[
        {"role": "user", "content": "小林今年 28 岁,提取姓名和年龄。"}
    ],
    response_format={
        "type": "json_schema",
        "json_schema": {
            "name": "person",
            "strict": True,
            "schema": {
                "type": "object",
                "properties": {
                    "name": {"type": "string"},
                    "age": {"type": "integer"},
                },
                "required": ["name", "age"],
                "additionalProperties": False,
            },
        },
    },
)

person = json.loads(completion.choices[0].message.content or "{}")
print(person)

additionalProperties: falsepuede evitar que el modelo agregue campos distintos al esquema, lo cual es adecuado para la extracción de datos, el llenado de formularios y la automatización posterior.

Implementar un bucle mínimo de llamada de herramienta

Configurartool_choice="required"en la primera pasada requiere que el modelo llame a la herramienta al menos una vez. Después de ejecutar la herramienta, debe conservar el mensaje completo del asistente y agregar un mensaje de herramienta contool_call_idcoincidente para cada llamada.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
import json
from typing import Any

tools: list[dict[str, Any]] = [
    {
        "type": "function",
        "function": {
            "name": "get_weather",
            "description": "查询城市天气",
            "parameters": {
                "type": "object",
                "properties": {"city": {"type": "string"}},
                "required": ["city"],
            },
        },
    }
]

messages: list[Any] = [
    {"role": "user", "content": "今天上海天气如何?"}
]

first = client.chat.completions.create(
    model="kimi-k3",
    messages=messages,
    tools=tools,
    tool_choice="required",
)

assistant_message = first.choices[0].message
messages.append(assistant_message)

for tool_call in assistant_message.tool_calls or []:
    arguments = json.loads(tool_call.function.arguments)
    result = json.dumps(
        {"city": arguments["city"], "weather": "sunny", "temperature_c": 32},
        ensure_ascii=False,
    )
    messages.append(
        {
            "role": "tool",
            "tool_call_id": tool_call.id,
            "content": result,
        }
    )

final = client.chat.completions.create(
    model="kimi-k3",
    messages=messages,
    tools=tools,
)

print(final.choices[0].message.content)

Los proyectos reales también necesitan verificar los parámetros de las herramientas, limitar los recursos accesibles, establecer tiempos de espera y agregar confirmación manual antes de realizar operaciones de alto riesgo, como escribir, eliminar y enviar.

Herramienta de carga dinámica

Si hay muchas herramientas, puede inyectar la definición completa de la herramienta a través del mensajesystemsincontentcuando la conversación llegue al punto requerido. La definición debe contenername,descriptionyparametersy persistir en el historial de solicitudes posteriores; el servidor no guardará esta definición para la aplicación.

Esta capacidad es adecuada para agentes grandes: primero proporcione una pequeña cantidad de herramientas básicas, confirme la dirección de la tarea y luego cargue la base de datos, el navegador o las herramientas del sistema empresarial, lo que reduce la cantidad de descripciones de herramientas enviadas al principio.

Contexto de 1M y almacenamiento en caché automático

Las solicitudes de modelo normales intentan automáticamente el almacenamiento en caché de contexto y no requieren proporcionar un ID de caché, TTL ni parámetros adicionales. Para mejorar las posibilidades de un acierto, coloque contenido más extenso y estable al principio de la solicitud y mantenga este prefijo sin cambios en solicitudes posteriores.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
from pathlib import Path

knowledge = Path("knowledge-base.md").read_text(encoding="utf-8")

for question in ["总结主要结论。", "列出三个实施风险。"]:
    completion = client.chat.completions.create(
        model="kimi-k3",
        messages=[
            {"role": "system", "content": knowledge},
            {"role": "user", "content": question},
        ],
    )
    print(completion.choices[0].message.content)

Un millón de tokens es el límite superior de capacidad, lo que no significa que cada solicitud deba estar llena de contexto. Realizar primero la selección de archivos, la recuperación segmentada y la deduplicación de resultados generalmente puede reducir las demoras y los costos, así como también reducir la interferencia de contenido irrelevante.

Limitaciones actuales y consideraciones de migración

Se recomienda comprobar punto por punto las siguientes restricciones antes de acceder:

  • K3 siempre habilita el modo de pensamiento,reasoning_effortactualmente solo admitemax;
  • max_completion_tokens tiene como valor predeterminado 131072 y admite un máximo de 1048576;
  • temperature=1.0, top_p=0.95, n=1, presence_penalty=0 y frequency_penalty=0 son valores fijos; omítalos en la solicitud;
  • Múltiples rondas de diálogo y llamadas de herramientas deben devolver el mensaje completo del asistente tal como está;
  • La entrada visual no admite URL de imágenes públicas; se debe utilizar Base64 oms://<file-id>;
  • La herramienta de búsqueda web oficial de Kimi se está actualizando y actualmente no se recomienda su uso en flujos de trabajo de producción recientes.

Si el proyecto anterior usa K2.x, busque primero thinking, los parámetros de muestreo y el código que conserva únicamente content. Después añada pruebas para el streaming de reasoning_content, el formato de matriz del contenido visual y el ciclo completo de llamadas a herramientas.

Preguntas frecuentes

¿Puede Kimi K3 usar OpenAI SDK directamente?

Sí. Instale openai>=1.0, configure base_url como https://api.moonshot.ai/v1 y pase la clave mediante MOONSHOT_API_KEY.

¿Por qué falla la solicitud después de configurar temperature?

Los parámetros de muestreo de K3, comotemperatureytop_p, adoptan valores fijos. Se recomienda oficialmente omitir estos campos y no copiar la configuración común de otros modelos compatibles con OpenAI.

¿Se pueden cargar las imágenes directamente en la dirección HTTP?

No. Codifique la imagen local como una URL de datos Base64 o cargue el archivo y utilice ms://<file-id>.

¿Necesito habilitar manualmente el almacenamiento en caché para el contexto de 1M?

No. Las solicitudes normales intentan usar la caché automáticamente. Mantener sin cambios un prefijo largo ayuda a que las solicitudes posteriores encuentren una coincidencia en la caché.

¿Cómo se factura Kimi K3?

Kimi aplica precios de pago por uso sin niveles según la longitud dentro de la ventana de 1 millón de tokens. La entrada distingue entre aciertos y fallos de caché, y la salida se factura por token. Los precios pueden cambiar; consulte la página de Kimi K3 Pricing antes de usarlo.

记录并分享
Creado con Hugo
Tema Stack diseñado por Jimmy