Persona d'IA Discourse, support de téléchargement

Vous pouvez désormais inclure de grands blocs de texte dans vos personas d’IA !

Cela offre plusieurs avantages :

  1. Vous pouvez introduire de grands blocs de texte dans vos bots d’IA personnalisés qui sont absents de l’entraînement des modèles. (par exemple : documents de formation internes, rapports internes)

  2. Vous pouvez mieux ancrer un persona avec des données concrètes (même si elles existent dans l’ensemble d’entraînement du modèle), ce qui peut aider le modèle à citer correctement des informations spécifiques et à améliorer la qualité des résultats.

Pour ajouter des téléchargements :

  1. Créez un nouveau persona en utilisant l’interface /admin/plugins/discourse-ai/ai-personas/.

  2. Téléchargez les fichiers texte que vous souhaitez inclure dans votre persona

:information_source: Avant de télécharger des fichiers, veuillez ajouter les extensions pertinentes ( .md et .txt) via le paramètre du site authorized extensions afin qu’il puisse être utilisé par le persona

  1. Ajustez les options d’indexation selon vos besoins

Pré-requis

Pour que l’option fonctionne, vous devez avoir configuré ai_embeddings_enabled et un ai_embeddings_model.

Discourse AI prend en charge un très grand nombre de modèles d’intégration.

Nos clients hébergés bénéficient d’un accès gratuit au modèle de pointe bge-large-en.

Les auto-hébergeurs ou ceux qui souhaitent plus de choix peuvent auto-héberger un modèle d’intégration ou utiliser des modèles d’Open AI, de Google (Gemini) et plus encore.

Est-ce un RAG ?

L’implémentation de notre support de téléchargement est en effet une Génération Augmentée par Récupération.

À un niveau élevé, chaque fois que nous sommes sur le point de demander à un LLM de répondre à la question d’un utilisateur, nous recherchons des informations très pertinentes basées sur le texte que vous avez entré et nous les injectons dans l’invite système.

Explication des différentes options d’indexation

Qu’est-ce qu’un token ? Les tokens sont des primitives utilisées par les grands modèles linguistiques pour diviser le texte. Une excellente explication visuelle se trouve ici : https://platform.openai.com/tokenizer

L’implémentation de téléchargement de Discourse AI est livrée avec les options suivantes :

Upload Chunk Tokens : après le téléchargement des fichiers, nous les divisons en morceaux. Cela vous permet de contrôler la taille des morceaux. Si un morceau est trop grand pour votre modèle d’intégration, l’intégration sera tronquée (seule une partie des tokens sera traitée).

Upload Chunk Overlap Tokens : il s’agit du nombre de tokens inclus du morceau précédent dans le morceau actuel. Plus ce nombre est élevé, plus la quantité d’informations dupliquées sera stockée dans votre index.

Search Conversation Chunks : cela contrôle le nombre de “morceaux” de tokens qui seront inclus sans condition en fonction de leur pertinence dans l’invite de complétion. Plus le nombre est élevé, plus le contexte fourni au LLM sera important (et plus les appels seront coûteux). Par exemple : Si ce paramètre est défini sur 10 et Upload Chunk Tokens sur 200, chaque complétion aura un surcoût de 2000 tokens.

Comment Discourse AI divise-t-il les blocs de texte ?

Discourse utilise un “Recursive Character Text Splitter”, qui tente de conserver les paragraphes, puis les lignes et enfin les mots ensemble lors de la division.

De plus, Discourse vous donne un contrôle supplémentaire sur la manière dont votre texte sera divisé.

Le séparateur [[metadata VOTRE MÉTA-DONNÉE ICI]] peut être utilisé pour diviser de grands blocs de texte et mettre en évidence correctement ce que chaque section couvre.

Par exemple :

[[metadata sur les chats]]
une longue histoire sur les chats
[[metadata sur les chiens]]
une longue histoire sur les chiens

Cela permet à un seul document texte de couvrir une grande variété de contenu et vous protège de la “contamination des chunks”. Vous avez la garantie que seules les données sur les chats seront incluses dans les chunks sur les chats et les chiens dans les chunks sur les chiens.

Cela semble compliqué, comment puis-je déboguer cela ?

Discourse AI est livré avec le paramètre du site ai bot debugging enabled groups, les utilisateurs de ce groupe ont accès au débogage de l’IA :

Les écrans de débogage de l’IA peuvent vous donner un aperçu des informations que nous envoyons à l’IA.

:warning: Garbage in - Garbage out Si vous fournissez des informations inutiles ou vagues à un LLM, il ne peut pas les convertir magiquement en informations utiles.

Cet écran peut vous aider à mieux décider de la taille de vos chunks ou si vous incluez trop ou trop peu de chunks.

Est-ce que cela fonctionne ?

Un exemple concret est la division de la documentation HAProxy et son intégration dans un persona :

Invite système :

Vous êtes un bot spécialisé dans la réponse aux questions sur HAProxy.

Vous vivez sur un forum Discourse et rendez le markdown Discourse.

Lorsque vous fournissez des réponses, essayez toujours d’inclure des liens vers la documentation HAProxy.

Par exemple, voici comment vous lieriez à la section 10.1.1. Gardez à l’esprit que vous pouvez lier à une section ou à une option à l’intérieur.

[fcgi-app](https://www.haproxy.com/documentation/haproxy-configuration-manual/latest/#10.1.1-fcgi-app)

Soyez généreux avec les liens, ils sont très utiles.

Contenu du téléchargement :
processed-haproxy-2.txt (1,2 Mo)

Qui a été généré en utilisant le script suivant :

file_content = File.read("configuration.txt")

title = nil
body = nil
last_line = nil

sections = []

file_content.each_line do |line|
  if line.strip.match?(/^[-]+$/)
    section_number, title = title.to_s.split(" ", 2)
    sections << {
      section_number: section_number,
      title: title,
      body: body.to_s.strip
    }

    title = last_line
    body = nil
    last_line = nil
  else
    body = body.to_s + last_line.to_s
    last_line = line
  end
end

section_number, title = title.to_s.split(" ", 2)
sections << { section_number: section_number, title: title, body: body }

section_names =
  sections.map { |section| [section[:section_number], section[:title]] }.to_h

sections[4..-1].each do |section|
  title = []
  current = +"".freeze
  section_number = section[:section_number]
  section_number
    .split(".")
    .each do |number|
      current << number
      current << "."
      title << section_names[current].to_s.strip
    end
  title = title.join(" - ")

  body = section[:body]

  next if body.strip.empty?
  puts "[[metadata section=\"#{section_number}\" title=\"#{title.strip}\"]]"
  puts body
end

Claude Opus et GPT-4 peuvent tous deux échouer lamentablement avec des questions complexes. C’est compréhensible car ils se nourrissent de tous les tokens sur Internet, donc 50 versions différentes de la documentation HAProxy et toutes les discussions du monde à son sujet entrent dans leur cerveau, ce qui peut les rendre très confus :

Exemples de GPT-4 et Claude 3 Opus confus

Tous deux sont objectivement bien moins bons que la réponse affinée fournie par le RAG de Discourse :

Exemples de GPT-4 et Claude Opus moins confus

L’avenir

Nous attendons avec impatience vos commentaires. Voici quelques idées pour l’avenir :

  • Support PDF/DOCX/XLS etc. pour que vous n’ayez pas besoin de convertir en texte
  • Chunking plus intelligent pour le code source / HTML
  • Transformations intelligentes des données entrantes avant l’indexation

Faites-nous savoir ce que vous en pensez !

Un grand merci à @Roman pour avoir mis en œuvre cette fonctionnalité :hugs:

24 « J'aime »

Serait-il possible, en plus du texte téléchargé manuellement, d’inclure les publications de forum qui correspondent à des critères sélectionnés ?

Comme :

  • dans une catégorie donnée
  • a un certain tag (ou, n’en a pas)
  • fait partie d’un sujet marqué comme résolu (alternativement, est spécifiquement une publication de solution)
  • est le sujet OP, pas une réponse
  • est publié par un utilisateur d’un groupe donné
  • est avant ou après une certaine date

Ou peut-être au lieu de cases à cocher avec ces éléments, simplement “est l’un des N meilleurs sujets pour une recherche de forum donnée” ?

1 « J'aime »

Tout cela est réalisable aujourd’hui avec une commande de recherche personnalisée :

  • La catégorie donnée peut être sélectionnée dans le filtre
  • tag
  • résolu
  • op uniquement (je pense que c’est faisable)
  • groupe donné
  • avant et après la date

:hugs:

5 « J'aime »

Hmmm, peut-être que je ne comprends pas bien. Est-ce que le fait de rendre cela disponible pour le persona fait la même chose ?

J’ai essayé, et la plupart du temps, je n’obtiens que Mistral qui invente des titres de sujets et renvoie à des numéros de publication totalement aléatoires. :slight_smile:

1 « J'aime »

Est-ce que Mistral est vraiment suffisant pour ces tâches ? Je pense que cela pourrait causer des hallucinations. Sam a raison, en modifiant la requête de base, vous pouvez faire tout ce que vous avez indiqué dans le message d’origine.

1 « J'aime »

Et, j’ai posté avant d’avoir fini ma pensée. La question était : fournir la commande de recherche et ses paramètres fait-il efficacement la même chose que fournir des fichiers téléchargés ?

Mais oui, Mistral n’est peut-être pas assez bon.

1 « J'aime »

Pour développer un peu ici :

https://chat.lmsys.org/?leaderboard

Mistral se décline en plusieurs versions… il y a Mistral 7b, Mixtral 8x7b (celle que vous avez), et le tout nouveau mistralai/Mixtral-8x22B-Instruct-v0.1 · Hugging Face - celui-ci et 5/6 autres modèles qu’ils publient, y compris certains à code source fermé.

Il faut être prudent avec un « Mistral pas assez bon » et toujours clarifier.

Je dirais que Mixtral-8x7b n’est tout simplement pas un bon choix pour le support d’outils, il s’en écarte trop.

Je dirais qu’il est :

  1. Plutôt bon pour le support « d’upload »
  2. Très bon pour le support de personas personnalisés
  3. Faible en support d’outils

Nous essayons de voir si nous pouvons passer à 8x22b (il est livré avec un bon support d’outils), le problème est que les exigences en mémoire sont assez élevées et nous devrions quantifier le modèle pour qu’il s’adapte bien à nos serveurs.

Mais vraiment… si vous avez un accord de confidentialité des données avec Amazon, je recommanderais fortement Bedrock, qui vous donnerait accès à Claude 3 Opus et Haiku.

Je comprends la tension entre les modèles open source et les modèles à code source fermé. C’est difficile, les modèles à code source fermé ont une longueur d’avance pour le moment.

2 « J'aime »

Vous avez raison, j’aurais dû mieux formuler. Je faisais effectivement allusion au fait que les modèles propriétaires sont meilleurs en général.

2 « J'aime »

Le téléchargement de plusieurs fichiers .txt à la fois pose problème : ils apparaissent rapidement, mais un seul est ensuite affiché, et le bouton “Ajouter un fichier” ne répond plus.

Je pense également que la prise en charge des fichiers .md serait un excellent ajout.

1 « J'aime »

Oh zut… bien vu @Roman, je vais regarder ça.

Cela devrait fonctionner, c’est déjà pris en charge, il vous suffit d’activer l’extension.

3 « J'aime »

J’ai poussé un correctif pour le bug multi-fichiers :

4 « J'aime »

2 messages ont été déplacées vers un nouveau sujet : Amélioration de la qualité des filtres de recherche dans Discourse AI

Salut Sam, je me demande comment cela fonctionne exactement. Cela indiquera à l’IA qu’il s’agit de données sur des chats ou des chiens, mais comment cela affectera-t-il les morceaux s’ils sont déjà définis sur un nombre fixe de jetons (disons 2000). Coupera-t-il un morceau lorsqu’il verra une ligne comme [[metadata sur les chiens]] et commencera-t-il un nouveau morceau ?

1 « J'aime »

Oui, il sera coupé tôt

2 « J'aime »

Oh zut, j’utilisais le format <meta>content</meta> qui fonctionne pour la plupart des modèles LLM, y a-t-il une raison pour laquelle vous avez choisi la méthode [[entre crochets]] ? Les <tags> fonctionnent-ils toujours ou est-il préférable d’utiliser la méthode entre crochets dans Discourse ?

1 « J'aime »

Ceci n’est pas du tout consommé par le LLM (nous analysons et consommons les métadonnées) voulait un séparateur très peu susceptible d’apparaître dans les données indexées

2 « J'aime »

Ajouté ceci à la copie

1 « J'aime »

Ces embeddings créés pour les personas IA se trouvent-ils dans la même base de données vectorielle ? Et en fait, tous les embeddings générés pour Discourse sont-ils stockés dans la même base de données vectorielle ?

1 « J'aime »

Tout en Postgres en utilisant la même base de données

2 « J'aime »

Quelqu’un peut-il me dire ce qu’il advient des fichiers texte téléchargés dans les personas s’ils sont supprimés de la liste des fichiers téléchargés ? Je comprends qu’ils sont utilisés pour le RAG, mais si je supprime le fichier, cela le supprimera-t-il de ce qui a été indexé ? Je me demande s’il est possible de modifier ce qui est indexé en supprimant un fichier texte, en apportant votre ajustement et en le téléchargeant à nouveau ?

1 « J'aime »