Partager via


Travailler avec des modèles de complétions de conversation

Les modèles de conversation sont des modèles de langage optimisés pour les interfaces conversationnelles. Les modèles se comportent différemment des anciens modèles d’API d’achèvement. Les modèles précédents étaient de type entrée de texte et sortie de texte, ce qui signifie qu’ils acceptaient une chaîne de prompt et retournaient une complétion à ajouter au prompt. Toutefois, les derniers modèles sont basés sur les conversations entrantes et les messages sortants. Les modèles attendent des données d’entrée formatées selon un format spécifique de transcription de type conversation. Ils retournent une complétion qui représente un message écrit par le modèle dans la conversation. Ce format a été conçu spécifiquement pour les conversations à plusieurs tours, mais il peut également bien fonctionner dans le cadre d’autres scénarios que celui des conversations.

Cet article vous guide tout au long de la prise en main des modèles de saisie semi-automatique de conversation. Pour obtenir les meilleurs résultats possible, utilisez les techniques décrites ici. N’essayez pas d’interagir avec les modèles de la même façon qu’avec les anciennes séries de modèles, car les modèles font souvent preuve de verbosité, et fournissent des réponses moins utiles.

Prerequisites

  • Un modèle d’achèvement de conversation Azure OpenAI déployé.
  • Installez la bibliothèque Python OpenAI : pip install openai.
  • Pour l’authentification microsoft Entra ID, installez Azure Identity : pip install azure-identity.
  • Pour l’exemple de comptage de jetons, installez tiktoken : pip install tiktoken.
  • Si vous utilisez des clés API, définissez la variable d’environnement AZURE_OPENAI_API_KEY .
  • Kit de développement logiciel (SDK) .NET 8.0 ou version ultérieure.
  • Pour l’authentification d’ID Microsoft Entra, installez Azure CLI et attribuez le Cognitive Services User rôle à votre compte d’utilisateur.
  • Si vous utilisez des clés API, définissez la variable d’environnement AZURE_OPENAI_API_KEY .

Travailler avec des modèles de saisie semi-automatique de conversation

L’extrait de code suivant montre la façon la plus simple d’interagir avec des modèles qui utilisent l’API de saisie semi-automatique de conversation.

Note

L’API réponses utilise le même style d'interaction conversationnelle, mais prend en charge les fonctionnalités les plus récentes qui ne sont pas prises en charge avec l'ancienne API de complétions de conversation.

from openai import OpenAI
from azure.identity import DefaultAzureCredential, get_bearer_token_provider

token_provider = get_bearer_token_provider(
    DefaultAzureCredential(), "https://ai.azure.com/.default"
)

client = OpenAI(  
  base_url = "https://YOUR-RESOURCE-NAME.openai.azure.com/openai/v1/",  
  api_key=token_provider,
)

response = client.chat.completions.create(
  model="YOUR-DEPLOYMENT-NAME",  # Replace with your model deployment name.
    messages=[
        {"role": "system", "content": "Assistant is a large language model trained by OpenAI."},
        {"role": "user", "content": "Who were the founders of Microsoft?"}
    ]
)

#print(response)
print(response.model_dump_json(indent=2))
print(response.choices[0].message.content)
{
  "id": "chatcmpl-8GHoQAJ3zN2DJYqOFiVysrMQJfe1P",
  "choices": [
    {
      "finish_reason": "stop",
      "index": 0,
      "message": {
        "content": "Microsoft was founded by Bill Gates and Paul Allen. They established the company on April 4, 1975. Bill Gates served as the CEO of Microsoft until 2000 and later as Chairman and Chief Software Architect until his retirement in 2008, while Paul Allen left the company in 1983 but remained on the board of directors until 2000.",
        "role": "assistant",
        "function_call": null
      },
      "content_filter_results": {
        "hate": {
          "filtered": false,
          "severity": "safe"
        },
        "self_harm": {
          "filtered": false,
          "severity": "safe"
        },
        "sexual": {
          "filtered": false,
          "severity": "safe"
        },
        "violence": {
          "filtered": false,
          "severity": "safe"
        }
      }
    }
  ],
  "created": 1698892410,
  "model": "gpt-4o",
  "object": "chat.completion",
  "usage": {
    "completion_tokens": 73,
    "prompt_tokens": 29,
    "total_tokens": 102
  },
  "prompt_filter_results": [
    {
      "prompt_index": 0,
      "content_filter_results": {
        "hate": {
          "filtered": false,
          "severity": "safe"
        },
        "self_harm": {
          "filtered": false,
          "severity": "safe"
        },
        "sexual": {
          "filtered": false,
          "severity": "safe"
        },
        "violence": {
          "filtered": false,
          "severity": "safe"
        }
      }
    }
  ]
}
Microsoft was founded by Bill Gates and Paul Allen. They established the company on April 4, 1975. Bill Gates served as the CEO of Microsoft until 2000 and later as Chairman and Chief Software Architect until his retirement in 2008, while Paul Allen left the company in 1983 but remained on the board of directors until 2000.

Chaque réponse inclut finish_reason. Les valeurs possibles pour finish_reason sont les suivantes :

  • stop : l’API a retourné la sortie complète du modèle.
  • length : sortie de modèle incomplète en raison du paramètre max_tokens ou de la limite relative aux jetons.
  • content_filter : contenu omis en raison d’un indicateur dans nos filtres de contenu.
  • null : réponse de l’API toujours en cours ou incomplète.

Envisagez de définir max_tokens une valeur légèrement plus élevée que la normale. Une valeur plus élevée permet de garantir que le modèle ne s’arrête pas de générer du texte avant d’avoir atteint la fin du message.

Travailler avec l’API Complétion de conversation

OpenAI a entraîné les modèles de complétion de conversation pour accepter les entrées formatées comme une conversation. Le paramètre messages prend un tableau d’objets de message avec une conversation organisée par rôle. Quand vous utilisez l’API Python, une liste de dictionnaires est utilisée.

Le format d’une complétion de conversation de base est le suivant :

{"role": "system", "content": "Provide some context and/or instructions to the model"},
{"role": "user", "content": "The user's message goes here"}

Une conversation avec un exemple de réponse suivie d’une question ressemblerait à ceci :

{"role": "system", "content": "Provide some context and/or instructions to the model."},
{"role": "user", "content": "Example question goes here."},
{"role": "assistant", "content": "Example answer goes here."},
{"role": "user", "content": "First question/message for the model to actually respond to."}

Rôle du système

Le rôle système, également appelé message système, est inclus au début du tableau. Ce message fournit les instructions initiales au modèle. Vous pouvez fournir diverses informations dans le rôle système, par exemple :

  • Une brève description de l’assistant.
  • Les traits de personnalité de l’assistant.
  • Les instructions ou règles à suivre par l’assistant.
  • Les données ou informations nécessaires au modèle, par exemple des questions pertinentes provenant d’un FAQ.

Vous pouvez personnaliser le rôle système en fonction de votre cas d’usage ou inclure des instructions de base. Le rôle/message système est facultatif, mais nous vous recommandons d’en inclure au moins un, même de base, pour obtenir les meilleurs résultats possible.

Messages

Après le rôle système, vous pouvez inclure une série de messages entre le user et le assistant.

 {"role": "user", "content": "What is thermodynamics?"}

Pour déclencher une réponse du modèle, finissez par un message de l’utilisateur afin d’indiquer que c’est au tour de l’assistant de répondre. Vous pouvez également inclure une série d’exemples de messages entre l’utilisateur et l’assistant pour effectuer un apprentissage en quelques essais.

Exemples de messages d'invite

La section suivante présente des exemples de différents styles de prompts que vous pouvez utiliser avec des modèles de complétions de conversation. Ces exemples ne sont qu’un point de départ. Vous pouvez faire des essais avec différents prompts pour personnaliser le comportement en fonction de vos propres cas d’usage.

Exemple de base

Si vous souhaitez que votre modèle de complétion de chat se comporte de la même façon que chatgpt.com, vous pouvez utiliser un message système de base comme Assistant is a large language model trained by OpenAI.

{"role": "system", "content": "Assistant is a large language model trained by OpenAI."},
{"role": "user", "content": "Who were the founders of Microsoft?"}

Exemple avec des instructions

Pour certains scénarios, vous pouvez être amené à donner plus d’instructions au modèle afin de définir des garde-fous permettant de déterminer ce que le modèle est capable de faire.

{"role": "system", "content": "Assistant is an intelligent chatbot designed to help users answer their tax related questions.
Instructions: 
- Only answer questions related to taxes. 
- If you're unsure of an answer, you can say "I don't know" or "I'm not sure" and recommend users go to the IRS website for more information. "},
{"role": "user", "content": "When are my taxes due?"}

Utiliser des données pour l’ancrage

Vous pouvez également inclure des données ou des informations pertinentes dans le message système afin de donner au modèle un contexte supplémentaire pour la conversation. Si vous devez inclure uniquement une petite quantité d’informations, vous pouvez les coder en dur dans le message système. Si vous disposez d’une grande quantité de données dont le modèle doit avoir connaissance, vous pouvez utiliser des incorporations ou un produit comme Recherche Azure AI pour récupérer les informations les plus pertinentes au moment de la requête.

{"role": "system", "content": "Assistant is an intelligent chatbot designed to help users answer technical questions about Azure OpenAI in Microsoft Foundry Models. Only answer questions using the context below and if you're not sure of an answer, you can say 'I don't know'.

Context:
- Azure OpenAI provides REST API access to OpenAI's powerful language models including the GPT-3, Codex and Embeddings model series.
- Azure OpenAI gives customers advanced language AI with OpenAI GPT-3, Codex, and DALL-E models with the security and enterprise promise of Azure. Azure OpenAI co-develops the APIs with OpenAI, ensuring compatibility and a smooth transition from one to the other.
- At Microsoft, we're committed to the advancement of AI driven by principles that put people first. Microsoft has made significant investments to help guard against abuse and unintended harm, which includes requiring applicants to show well-defined use cases, incorporating Microsoft’s principles for responsible AI use."
},
{"role": "user", "content": "What is Azure OpenAI?"}

Apprentissage en quelques essais avec la complétion de conversation

Vous pouvez également fournir quelques exemples rapides au modèle. L’approche de l’apprentissage en quelques essais a légèrement changé en raison du nouveau format de prompt. Vous pouvez désormais inclure une série de messages entre l’utilisateur et l’assistant dans le prompt sous la forme d’un petit nombre d’exemples. Vous pouvez utiliser ces exemples pour fournir des réponses aux questions courantes afin de préparer le modèle, ou de lui enseigner des comportements particuliers.

Cet exemple montre comment utiliser l’apprentissage en quelques essais avec GPT-35-Turbo et GPT-4. Vous pouvez expérimenter différentes approches afin de déterminer celle qui convient le mieux à votre cas d’usage.

{"role": "system", "content": "Assistant is an intelligent chatbot designed to help users answer their tax related questions. "},
{"role": "user", "content": "When do I need to file my taxes by?"},
{"role": "assistant", "content": "In 2023, you will need to file your taxes by April 18th. The date falls after the usual April 15th deadline because April 15th falls on a Saturday in 2023. For more details, see https://www.irs.gov/filing/individuals/when-to-file."},
{"role": "user", "content": "How can I check the status of my tax refund?"},
{"role": "assistant", "content": "You can check the status of your tax refund by visiting https://www.irs.gov/refunds"}

Utiliser la complétion de conversation pour des scénarios autres que les conversations

L’API de complétion de conversation est conçue pour être utilisée avec des invites multitours, mais elle fonctionne tout aussi bien dans les scénarios non basés sur une conversation.

Par exemple, pour un scénario d’extraction d’entités, vous pouvez utiliser cette prompt :

{"role": "system", "content": "You are an assistant designed to extract entities from text. Users will paste in a string of text and you will respond with entities you've extracted from the text as a JSON object. Here's an example of your output format:
{
   "name": "",
   "company": "",
   "phone_number": ""
}"},
{"role": "user", "content": "Hello. My name is Robert Smith. I'm calling from Contoso Insurance, Delaware. My colleague mentioned that you are interested in learning about our comprehensive benefits policy. Could you give me a call back at (555) 346-9322 when you get a chance so we can go over the benefits?"}

Créer une boucle de conversation de base

Les exemples présentés jusqu’à maintenant montrent les mécanismes de base de l’interaction avec l’API de complétion de conversation. Cet exemple vous montre comment créer une boucle de conversation qui effectue les actions suivantes :

  • Accepte en continu l’entrée de la console, et la met en forme correctement dans le cadre de la liste des messages en tant que contenu de rôle utilisateur.
  • Génère des réponses qui sont imprimées dans la console et mises en forme et ajoutées à la liste de messages en tant que contenu de rôle d’assistant.

Chaque fois qu’une nouvelle question est posée, une transcription en continu de la conversation est envoyée avec la dernière question. Dans la mesure où le modèle n’a pas de mémoire, vous devez envoyer une transcription mise à jour avec chaque nouvelle question, sinon le modèle perd le contexte des questions et réponses précédentes.

from openai import OpenAI
from azure.identity import DefaultAzureCredential, get_bearer_token_provider

token_provider = get_bearer_token_provider(
    DefaultAzureCredential(), "https://ai.azure.com/.default"
)

client = OpenAI(  
  base_url = "https://YOUR-RESOURCE-NAME.openai.azure.com/openai/v1/",  
  api_key=token_provider,
)

conversation=[{"role": "system", "content": "You are a helpful assistant."}]

while True:
    user_input = input("Q:")      
    conversation.append({"role": "user", "content": user_input})

    response = client.chat.completions.create(
      model="YOUR-DEPLOYMENT-NAME",  # Replace with your model deployment name.
        messages=conversation
    )

    conversation.append({"role": "assistant", "content": response.choices[0].message.content})
    print("\n" + response.choices[0].message.content + "\n")

Quand vous exécutez le code précédent, vous obtenez une fenêtre de console vide. Entrez votre première question dans la fenêtre, puis sélectionnez la touche Enter. Une fois la réponse retournée, vous pouvez répéter le processus, et continuer à poser des questions.

Gérer les conversations

L’exemple précédent s’exécute jusqu’à ce que vous atteignez la limite de jeton du modèle (fenêtre de contexte). Avec chaque question posée et réponse reçue, la messages liste augmente en taille. Le nombre de jetons combinés de votre messages plus les jetons de sortie demandés doit rester dans la limite du modèle, ou la requête échoue. Consultez la page modèles pour connaître les limites de jeton actuelles.

Il vous appartient de vérifier que le prompt et la complétion ne dépassent pas la limite de jetons. Pour les conversations plus longues, vous devez effectuer le suivi du nombre de jetons, et envoyer uniquement au modèle un prompt compris dans la limite. Vous pouvez également utiliser l’API réponses pour vous permettre de gérer la troncation/la gestion de l’historique des conversations.

L’exemple de code suivant montre un exemple simple de boucle de conversation avec une technique permettant de gérer 4 096 jetons en utilisant la bibliothèque tiktoken d’OpenAI.

Vous devrez peut-être mettre à niveau votre version de tiktoken avec pip install tiktoken --upgrade.

import tiktoken
from openai import OpenAI
from azure.identity import DefaultAzureCredential, get_bearer_token_provider

token_provider = get_bearer_token_provider(
    DefaultAzureCredential(), "https://ai.azure.com/.default"
)

client = OpenAI(  
  base_url = "https://YOUR-RESOURCE-NAME.openai.azure.com/openai/v1/",  
  api_key=token_provider,
)

system_message = {"role": "system", "content": "You are a helpful assistant."}
max_response_tokens = 250
token_limit = 4096
conversation = []
conversation.append(system_message)

def num_tokens_from_messages(messages, model="gpt-4o"):
    """Return the number of tokens used by a list of messages."""
    try:
        encoding = tiktoken.encoding_for_model(model)
    except KeyError:
        print("Warning: model not found. Using o200k_base encoding.")
        encoding = tiktoken.get_encoding("o200k_base")
    
    if model in {
        "gpt-4o",
        "gpt-4o-mini",
        "gpt-5",
        "gpt-4.1",
        "o1",
        "o1-mini",
        "o3",
        "o3-mini",
        "o4-mini",
    }:
        tokens_per_message = 3
        tokens_per_name = 1

    elif any(model.startswith(prefix) for prefix in [
        "gpt-4o-", 
        "gpt-5-", 
        "gpt-4.1-",
        "o1-", 
        "o3-", 
        "o4-mini-",
    ]):
        tokens_per_message = 3
        tokens_per_name = 1
    else:
        raise NotImplementedError(
            f"""num_tokens_from_messages() is not implemented for model {model}. """
        )
    
    num_tokens = 0
    for message in messages:
        num_tokens += tokens_per_message
        for key, value in message.items():
            num_tokens += len(encoding.encode(value))
            if key == "name":
                num_tokens += tokens_per_name
    num_tokens += 3  
    return num_tokens

while True:
    user_input = input("Q:")      
    conversation.append({"role": "user", "content": user_input})
    conv_history_tokens = num_tokens_from_messages(conversation, model="gpt-4o")

    while conv_history_tokens + max_response_tokens >= token_limit:
        del conversation[1] 
        conv_history_tokens = num_tokens_from_messages(conversation, model="gpt-4o")

    response = client.chat.completions.create(
      model="YOUR-DEPLOYMENT-NAME",
        messages=conversation,
        temperature=0.7,
        max_tokens=max_response_tokens
    )

    conversation.append({"role": "assistant", "content": response.choices[0].message.content})
    print("\n" + response.choices[0].message.content + "\n")

Dans cet exemple, une fois le nombre de jetons atteint, les messages les plus anciens de la transcription de conversation sont supprimés. Par souci d’efficacité, del est utilisé à la place de pop(). Nous commençons à l’index 1 pour conserver en permanence le message système, et supprimer uniquement les messages de l’utilisateur ou de l’assistant. Au fil du temps, cette méthode de gestion de la conversation peut entraîner une détérioration de la qualité de la conversation, car le modèle perd progressivement le contexte des parties précédentes de la conversation.

Une autre approche consiste à limiter la durée de la conversation en fonction de la limite maximale de jetons ou d’un nombre spécifique de tours. Une fois la limite maximale de jetons atteinte, le modèle perd le contexte si vous permettez à la conversation de se poursuivre. Vous pouvez demander à l’utilisateur d’entamer une nouvelle conversation, et d’effacer la liste des messages pour démarrer une nouvelle conversation avec la totalité des jetons disponibles.

La partie de comptage de jetons du code présentée précédemment est une version simplifiée de l’un des exemples de livres de recettes d’OpenAI.

Résolution des problèmes

Désolé... Nous n’avons pas pu créer la saisie semi-automatique, car le modèle a généré une sortie Unicode non valide

Code d’erreur Message d’erreur Solution de contournement
500 500 - Erreur interne du serveur : Code d’erreur : 500 - {"erreur": {"message": "Échec de la création de la complétion car le modèle a généré une sortie Unicode non valide"}} Vous pouvez diminuer l’apparition de ces erreurs en réduisant la température de vos invites pour se situer à moins de 1 et en veillant à utiliser un client avec une logique de nouvelle tentative. Une nouvelle tentative de la requête aboutit souvent à une réponse correcte.

Erreurs courantes

  • 401/403 (authentification) : vérifiez votre clé API ou vérifiez que vous avez accès à l’ID Microsoft Entra à la ressource Azure OpenAI.
  • 400/404 (déploiement introuvable) : vérifiez qu’il model correspond à votre nom de déploiement.
  • URL non valide : vérifiez que cela base_url se termine par /openai/v1/.

Configurer

  1. Créez une application console .NET :

    dotnet new console -n chat-completions
    cd chat-completions
    
  2. Installez les packages NuGet requis :

    dotnet add package OpenAI --prerelease
    dotnet add package Azure.Identity
    
  3. Pour l’authentification sans clé avec l’ID Microsoft Entra, connectez-vous à Azure :

    az login
    

Travailler avec des modèles de saisie semi-automatique de conversation

L’extrait de code suivant montre la façon la plus simple d’interagir avec des modèles qui utilisent l’API de saisie semi-automatique de conversation.

Note

L'API des réponses utilise le même style d'interaction conversationnel, mais prend en charge les fonctionnalités les plus récentes non prises en charge par l'ancienne API de complétion de chat.

using Azure.Identity;
using OpenAI;
using OpenAI.Chat;
using System.ClientModel.Primitives;

#pragma warning disable OPENAI001

BearerTokenPolicy tokenPolicy = new(
    new DefaultAzureCredential(),
    "https://ai.azure.com/.default");

ChatClient client = new(
    model: "YOUR-DEPLOYMENT-NAME",
    authenticationPolicy: tokenPolicy,
    options: new OpenAIClientOptions()
    {
        Endpoint = new Uri("https://YOUR-RESOURCE-NAME.openai.azure.com/openai/v1/")
    }
);

ChatCompletion completion = await client.CompleteChatAsync(
[
    new SystemChatMessage("Assistant is a large language model trained by OpenAI."),
    new UserChatMessage("Who were the founders of Microsoft?"),
]);

Console.WriteLine(completion.Content[0].Text);
Microsoft was founded by Bill Gates and Paul Allen. They established the company on April 4, 1975. Bill Gates served as the CEO of Microsoft until 2000 and later as Chairman and Chief Software Architect until his retirement in 2008, while Paul Allen left the company in 1983 but remained on the board of directors until 2000.

Chaque réponse inclut un FinishReason. Les valeurs possibles pour FinishReason sont les suivantes :

  • Arrêt : l’API a retourné la sortie complète du modèle.
  • Longueur : sortie de modèle incomplète en raison soit du paramètre MaxOutputTokenCount soit de la limite de jetons.
  • ContentFilter : contenu omis en raison d’un indicateur de filtre de contenu.
  • null : réponse de l’API toujours en cours ou incomplète.

Envisagez de définir MaxOutputTokenCount une valeur légèrement plus élevée que la normale. Une valeur plus élevée permet de garantir que le modèle ne s’arrête pas de générer du texte avant d’avoir atteint la fin du message.

Travailler avec l’API Complétion de conversation

OpenAI a entraîné les modèles de complétion de conversation pour accepter les entrées formatées comme une conversation. Le paramètre messages prend un tableau d’objets de message avec une conversation organisée par rôle. Lorsque vous utilisez le Kit de développement logiciel (SDK) .NET, vous utilisez des classes de messages fortement typées pour chaque rôle.

Le format d’une complétion de conversation de base est le suivant :

new SystemChatMessage("Provide some context and/or instructions to the model"),
new UserChatMessage("The user's message goes here")

Une conversation avec un exemple de réponse suivie d’une question ressemblerait à ceci :

new SystemChatMessage("Provide some context and/or instructions to the model."),
new UserChatMessage("Example question goes here."),
new AssistantChatMessage("Example answer goes here."),
new UserChatMessage("First question/message for the model to actually respond to.")

Rôle du système

Le rôle système, également appelé message système, est inclus au début du tableau. Ce message fournit les instructions initiales au modèle. Vous pouvez fournir diverses informations dans le rôle système, par exemple :

  • Une brève description de l’assistant.
  • Les traits de personnalité de l’assistant.
  • Les instructions ou règles à suivre par l’assistant.
  • Les données ou informations nécessaires au modèle, par exemple des questions pertinentes provenant d’un FAQ.

Vous pouvez personnaliser le rôle système en fonction de votre cas d’usage ou inclure des instructions de base. Le rôle/message système est facultatif, mais nous vous recommandons d’en inclure au moins un, même de base, pour obtenir les meilleurs résultats possible.

Messages

Après le rôle système, vous pouvez inclure une série de messages entre le user et le assistant.

new UserChatMessage("What is thermodynamics?")

Pour déclencher une réponse du modèle, finissez par un message de l’utilisateur afin d’indiquer que c’est au tour de l’assistant de répondre. Vous pouvez également inclure une série d’exemples de messages entre l’utilisateur et l’assistant pour effectuer un apprentissage en quelques essais.

Exemples de messages d'invite

La section suivante présente des exemples de différents styles de prompts que vous pouvez utiliser avec des modèles de complétions de conversation. Ces exemples ne sont qu’un point de départ. Vous pouvez faire des essais avec différents prompts pour personnaliser le comportement en fonction de vos propres cas d’usage.

Exemple de base

Si vous souhaitez que votre modèle de complétion de chat se comporte de la même façon que chatgpt.com, vous pouvez utiliser un message système de base comme Assistant is a large language model trained by OpenAI.

new SystemChatMessage("Assistant is a large language model trained by OpenAI."),
new UserChatMessage("Who were the founders of Microsoft?")

Exemple avec des instructions

Pour certains scénarios, vous pouvez être amené à donner plus d’instructions au modèle afin de définir des garde-fous permettant de déterminer ce que le modèle est capable de faire.

new SystemChatMessage(@"Assistant is an intelligent chatbot designed to help users answer their tax related questions.
Instructions:
- Only answer questions related to taxes.
- If you're unsure of an answer, you can say ""I don't know"" or ""I'm not sure"" and recommend users go to the IRS website for more information."),
new UserChatMessage("When are my taxes due?")

Utiliser des données pour l’ancrage

Vous pouvez également inclure des données ou des informations pertinentes dans le message système afin de donner au modèle un contexte supplémentaire pour la conversation. Si vous devez inclure uniquement une petite quantité d’informations, vous pouvez les coder en dur dans le message système. Si vous disposez d’une grande quantité de données dont le modèle doit avoir connaissance, vous pouvez utiliser des incorporations ou un produit comme Recherche Azure AI pour récupérer les informations les plus pertinentes au moment de la requête.

new SystemChatMessage(@"Assistant is an intelligent chatbot designed to help users answer technical questions about Azure OpenAI in Microsoft Foundry Models. Only answer questions using the context below and if you're not sure of an answer, you can say 'I don't know'.

Context:
- Azure OpenAI provides REST API access to OpenAI's powerful language models including the GPT-3, Codex and Embeddings model series.
- Azure OpenAI gives customers advanced language AI with OpenAI GPT-3, Codex, and DALL-E models with the security and enterprise promise of Azure. Azure OpenAI co-develops the APIs with OpenAI, ensuring compatibility and a smooth transition from one to the other.
- At Microsoft, we're committed to the advancement of AI driven by principles that put people first. Microsoft has made significant investments to help guard against abuse and unintended harm, which includes requiring applicants to show well-defined use cases, incorporating Microsoft's principles for responsible AI use."),
new UserChatMessage("What is Azure OpenAI?")

Apprentissage en quelques essais avec la complétion de conversation

Vous pouvez également fournir quelques exemples rapides au modèle. Vous pouvez inclure une série de messages entre l’utilisateur et l’Assistant dans l’invite à quelques exemples. Vous pouvez utiliser ces exemples pour fournir des réponses aux questions courantes afin de préparer le modèle, ou de lui enseigner des comportements particuliers.

new SystemChatMessage("Assistant is an intelligent chatbot designed to help users answer their tax related questions."),
new UserChatMessage("When do I need to file my taxes by?"),
new AssistantChatMessage("In 2023, you will need to file your taxes by April 18th. The date falls after the usual April 15th deadline because April 15th falls on a Saturday in 2023. For more details, see https://www.irs.gov/filing/individuals/when-to-file."),
new UserChatMessage("How can I check the status of my tax refund?"),
new AssistantChatMessage("You can check the status of your tax refund by visiting https://www.irs.gov/refunds")

Utiliser la complétion de conversation pour des scénarios autres que les conversations

L’API de complétion de conversation est conçue pour être utilisée avec des invites multitours, mais elle fonctionne tout aussi bien dans les scénarios non basés sur une conversation.

Par exemple, pour un scénario d’extraction d’entités, vous pouvez utiliser cette prompt :

new SystemChatMessage(@"You are an assistant designed to extract entities from text. Users will paste in a string of text and you will respond with entities you've extracted from the text as a JSON object. Here's an example of your output format:
{
   ""name"": """",
   ""company"": """",
   ""phone_number"": """"
}"),
new UserChatMessage("Hello. My name is Robert Smith. I'm calling from Contoso Insurance, Delaware. My colleague mentioned that you are interested in learning about our comprehensive benefits policy. Could you give me a call back at (555) 346-9322 when you get a chance so we can go over the benefits?")

Créer une boucle de conversation de base

Les exemples présentés jusqu’à maintenant montrent les mécanismes de base de l’interaction avec l’API de complétion de conversation. Cet exemple vous montre comment créer une boucle de conversation qui effectue les actions suivantes :

  • Accepte en continu l’entrée de la console, et la met en forme correctement dans le cadre de la liste des messages en tant que contenu de rôle utilisateur.
  • Génère des réponses qui sont imprimées dans la console et mises en forme et ajoutées à la liste de messages en tant que contenu de rôle d’assistant.

Chaque fois qu’une nouvelle question est posée, une transcription en continu de la conversation est envoyée avec la dernière question. Dans la mesure où le modèle n’a pas de mémoire, vous devez envoyer une transcription mise à jour avec chaque nouvelle question, sinon le modèle perd le contexte des questions et réponses précédentes.

using Azure.Identity;
using OpenAI;
using OpenAI.Chat;
using System.ClientModel.Primitives;

#pragma warning disable OPENAI001

BearerTokenPolicy tokenPolicy = new(
    new DefaultAzureCredential(),
    "https://ai.azure.com/.default");

ChatClient client = new(
    model: "YOUR-DEPLOYMENT-NAME",
    authenticationPolicy: tokenPolicy,
    options: new OpenAIClientOptions()
    {
        Endpoint = new Uri("https://YOUR-RESOURCE-NAME.openai.azure.com/openai/v1/")
    }
);

List<ChatMessage> conversation =
[
    new SystemChatMessage("You are a helpful assistant."),
];

while (true)
{
    Console.Write("Q: ");
    string? userInput = Console.ReadLine();
    if (string.IsNullOrWhiteSpace(userInput)) break;

    conversation.Add(new UserChatMessage(userInput));

    ChatCompletion response = await client.CompleteChatAsync(conversation);
    string assistantMessage = response.Content[0].Text;

    conversation.Add(new AssistantChatMessage(assistantMessage));
    Console.WriteLine($"\n{assistantMessage}\n");
}

Quand vous exécutez le code précédent, vous obtenez une fenêtre de console vide. Entrez votre première question dans la fenêtre, puis sélectionnez la touche Enter. Une fois la réponse retournée, vous pouvez répéter le processus, et continuer à poser des questions.

Gérer les conversations

L’exemple précédent s’exécute jusqu’à ce que la limite de jeton du modèle (fenêtre de contexte) soit atteinte. Avec chaque question posée et réponse reçue, la conversation liste augmente en taille. Le nombre combiné de jetons de vos messages ainsi que les jetons de sortie demandés doivent rester dans la limite du modèle, ou la requête échoue. Consultez la page modèles pour connaître les limites de jeton actuelles.

Il vous appartient de vérifier que le prompt et la complétion ne dépassent pas la limite de jetons. Pour les conversations plus longues, vous devez effectuer le suivi du nombre de jetons, et envoyer uniquement au modèle un prompt compris dans la limite. Vous pouvez également utiliser l’API réponses pour vous permettre de gérer la troncation et la gestion de l’historique des conversations.

L’exemple de code suivant montre un exemple de boucle de conversation simple qui supprime l’historique des conversations lorsque le nombre de messages stockés approche d’une limite. Il supprime les messages non système les plus anciens pour que la conversation reste dans les limites fixées.

Vous pouvez installer les packages Microsoft.ML.Tokenizers et Microsoft.ML.Tokenizers.Data.0200kBase pour le comptage de jetons précis :

dotnet add package Microsoft.ML.Tokenizers
dotnet add package Microsoft.ML.Tokenizers.Data.O200kBase
using Azure.Identity;
using Microsoft.ML.Tokenizers;
using OpenAI;
using OpenAI.Chat;
using System.ClientModel.Primitives;

#pragma warning disable OPENAI001

BearerTokenPolicy tokenPolicy = new(
    new DefaultAzureCredential(),
    "https://ai.azure.com/.default");

ChatClient client = new(
    model: "YOUR-DEPLOYMENT-NAME",
    authenticationPolicy: tokenPolicy,
    options: new OpenAIClientOptions()
    {
        Endpoint = new Uri("https://YOUR-RESOURCE-NAME.openai.azure.com/openai/v1/")
    }
);

const int MaxResponseTokens = 250;
const int TokenLimit = 4096;

var tokenizer = TiktokenTokenizer.CreateForModel("gpt-4o");

List<ChatMessage> conversation =
[
    new SystemChatMessage("You are a helpful assistant."),
];

static int CountTokens(TiktokenTokenizer tokenizer, IEnumerable<ChatMessage> messages)
{
    int count = 3; // base overhead for reply priming
    foreach (var message in messages)
    {
        count += 4; // per-message overhead
        string content = message switch
        {
            SystemChatMessage s => s.Content[0].Text ?? string.Empty,
            UserChatMessage u => u.Content[0].Text ?? string.Empty,
            AssistantChatMessage a => a.Content[0].Text ?? string.Empty,
            _ => string.Empty
        };
        count += tokenizer.CountTokens(content);
    }
    return count;
}

while (true)
{
    Console.Write("Q: ");
    string? userInput = Console.ReadLine();
    if (string.IsNullOrWhiteSpace(userInput)) break;

    conversation.Add(new UserChatMessage(userInput));

    int historyTokens = CountTokens(tokenizer, conversation);
    while (historyTokens + MaxResponseTokens >= TokenLimit && conversation.Count > 2)
    {
        conversation.RemoveAt(1); // remove oldest non-system message
        historyTokens = CountTokens(tokenizer, conversation);
    }

    ChatCompletionOptions options = new() { MaxOutputTokenCount = MaxResponseTokens };
    ChatCompletion response = await client.CompleteChatAsync(conversation, options);
    string assistantMessage = response.Content[0].Text;

    conversation.Add(new AssistantChatMessage(assistantMessage));
    Console.WriteLine($"\n{assistantMessage}\n");
}

Dans cet exemple, une fois le nombre de jetons atteint, les messages les plus anciens de la transcription de conversation sont supprimés. Nous conservons toujours le message système et supprimons uniquement les messages utilisateur ou assistant. Au fil du temps, cette méthode de gestion de la conversation peut entraîner une détérioration de la qualité de la conversation, car le modèle perd progressivement le contexte des parties précédentes de la conversation.

Une autre approche consiste à limiter la durée de la conversation en fonction de la limite maximale de jetons ou d’un nombre spécifique de tours. Une fois la limite maximale de jetons atteinte, le modèle perd le contexte si vous permettez à la conversation de se poursuivre. Vous pouvez demander à l’utilisateur d’entamer une nouvelle conversation, et d’effacer la liste des messages pour démarrer une nouvelle conversation avec la totalité des jetons disponibles.

Résolution des problèmes

Désolé... Nous n’avons pas pu créer la saisie semi-automatique, car le modèle a généré une sortie Unicode non valide

Code d’erreur Message d’erreur Solution de contournement
500 500 - Erreur interne du serveur : Code d’erreur : 500 - {"erreur": {"message": "Échec de la création de la complétion car le modèle a généré une sortie Unicode non valide"}} Vous pouvez réduire l’occurrence de ces erreurs en abaissant le Temperature dans votre ChatCompletionOptions à moins de 1 et en vous assurant que vous utilisez un client avec une logique de réessai. Une nouvelle tentative de la requête aboutit souvent à une réponse correcte.

Erreurs courantes

  • 401/403 (authentification) : vérifiez votre clé API ou vérifiez que vous avez accès à l’ID Microsoft Entra à la ressource Azure OpenAI.
  • 400/404 (déploiement introuvable) : vérifiez que le nom du modèle passé au constructeur correspond à ChatClient votre nom de déploiement.
  • Point de terminaison non valide : vérifiez que l’URI Endpoint en OpenAIClientOptions points vers https://YOUR-RESOURCE-NAME.openai.azure.com/openai/v1/.