Florian.Moret commited on
Commit
32660c3
·
1 Parent(s): dfe94ac

update medata context

Browse files
Files changed (1) hide show
  1. app.py +28 -21
app.py CHANGED
@@ -25,39 +25,34 @@ chunk_overlap = 15
25
  # 📌 Définition des chemins de stockage
26
  index_path = "faiss_index.bin"
27
  chunks_path = "chunked_docs.pkl"
 
 
28
 
29
  print("🔄 Chargement des données existantes...")
30
- index = faiss.read_index(index_path) # Charger l'index FAISS
31
  with open(chunks_path, "rb") as f:
32
- chunked_docs = pickle.load(f) # Charger les chunks de texte
33
- print(" Index et chunks chargés avec succès !")
34
-
 
 
35
 
36
  # 📌 Récupération des chunks les plus pertinents
37
  def retrieve_relevant_chunks(question, k=5):
38
- """Recherche les chunks les plus pertinents en fonction de la similarité des embeddings."""
39
  question_embedding_response = mistral_client.embeddings.create(
40
  model=model_embedding,
41
  inputs=[question],
42
  )
43
  question_embedding = np.array(question_embedding_response.data[0].embedding).astype('float32').reshape(1, -1)
44
-
45
- # Vérification de la compatibilité des dimensions
46
- dimension = index.d
47
- if question_embedding.shape[1] != dimension:
48
- raise ValueError(f"⚠️ ERREUR : La dimension de l'embedding de la question ({question_embedding.shape[1]}) ne correspond pas aux embeddings indexés ({dimension}).")
49
-
50
  distances, indices = index.search(question_embedding, k)
51
-
52
  if len(indices[0]) == 0:
53
  print("⚠️ Avertissement : Aucun chunk pertinent trouvé, réponse possible moins précise.")
54
- return []
55
-
56
  return [chunked_docs[i] for i in indices[0]]
57
  #endregion
58
 
59
  #region# Définition des prompts
60
- def generate_prompts(score:str, type: str, annee_min: str, annee_max:str, context ) -> dict:
61
  """
62
  Genere les prefixes et suffixes des prompts pour Mistral en fonction du score de vulgarisation, du type d'espece, et les années des documents
63
  Args:
@@ -77,14 +72,14 @@ def generate_prompts(score:str, type: str, annee_min: str, annee_max:str, contex
77
 
78
  if score == "1":
79
  prefix_prompt = f"""Tu es un assistant IA spécialisé en nutrition de la volaille. Ton utilisateur est un chercheur travaillant sur
80
- l'amélioration des régimes alimentaires pour optimiser la santé et la croissance des {type_description}. Voici des informations contextuelles à utiliser avec priorité : {context}.
81
  Réponds en vulgarisant les informations.
82
  Pour fournir la réponse, tu dois te baser sur des publications/articles qui ont une date de publication entre {annee_min} et {annee_max}."""
83
  suffix_prompt = """Réponds en français et donne une réponse directe et claire.
84
  Fini par faire une bibliographie avec les références bibliographiquesque tu as utilisé."""
85
  elif score == "2":
86
  prefix_prompt = f"""Tu es un assistant IA spécialisé en nutrition de la volaille. Ton utilisateur est un chercheur travaillant sur
87
- l'amélioration des régimes alimentaires pour optimiser la santé et la croissance des {type_description}. Voici des informations contextuelles à utiliser avec priorité : {context}.
88
  Réponds en fournissant des explications claires et concises, adaptées à la question posée.
89
  Pour fournir la réponse, tu dois te baser sur des publications/articles qui ont une date de publication entre {annee_min} et {annee_max}.
90
  Tes réponses doivent être structurées, complètes et adaptées aux professionnels du secteur."""
@@ -94,7 +89,7 @@ def generate_prompts(score:str, type: str, annee_min: str, annee_max:str, contex
94
  Fini par faire une bibliographie avec les références bibliographiques que tu as utilisé."""
95
  elif score == "3":
96
  prefix_prompt = f"""Tu es un assistant IA spécialisé en nutrition de la volaille. Ton utilisateur est un chercheur travaillant sur
97
- l'amélioration des régimes alimentaires pour optimiser la santé et la croissance des {type_description}. Voici des informations contextuelles à utiliser avec priorité : {context}.
98
  Réponds en fournissant des explications détaillées et précises, adaptées à la complexité de la question posée.
99
  N'oublie pas de citer à la fin de ta réponse les références sur lesquelles tu t'es basé avec son année (entre {annee_min} et {annee_max}).
100
  Tes réponses doivent être structurées, complètes et adaptées aux professionnels du secteur."""
@@ -269,9 +264,9 @@ choix_vulgarisation = st.sidebar.pills(
269
 
270
  #Années de publication
271
  choix_annee = st.sidebar.slider("Années de publication",
272
- min_value=2015,
273
  max_value=2025,
274
- value=(2020,2025))
275
  #endregion
276
 
277
  #region# Interface utilisateur
@@ -284,7 +279,9 @@ if st.button("Envoyer la question..."):
284
 
285
  #todo mettre relevant chunks et context =
286
  relevant_chunks= retrieve_relevant_chunks(user_input)
287
- context = "\n".join(relevant_chunks)
 
 
288
 
289
  response0 = prompt_pipeline(
290
  user_prompt = user_input,
@@ -315,6 +312,15 @@ if st.button("Envoyer la question..."):
315
  </div>
316
  """, unsafe_allow_html=True)
317
 
 
 
 
 
 
 
 
 
 
318
  response1 = prompt_pipeline(
319
  user_prompt = user_input,
320
  niveau_detail=choix_vulgarisation,
@@ -330,6 +336,7 @@ if st.button("Envoyer la question..."):
330
  {response1['reponse_propre']}
331
  </div>
332
  """, unsafe_allow_html=True)
 
333
  #encadré sources
334
  # # Afficher un titre
335
  # st.subheader("Sources :")
 
25
  # 📌 Définition des chemins de stockage
26
  index_path = "faiss_index.bin"
27
  chunks_path = "chunked_docs.pkl"
28
+ metadata_path = "metadata.pkl"
29
+ embeddings_path = "embeddings.npy"
30
 
31
  print("🔄 Chargement des données existantes...")
32
+ index = faiss.read_index(index_path)
33
  with open(chunks_path, "rb") as f:
34
+ chunked_docs = pickle.load(f)
35
+ with open(metadata_path, "rb") as f:
36
+ metadata_list = pickle.load(f)
37
+ embeddings = np.load(embeddings_path)
38
+ print("✅ Index, chunks, embeddings et métadonnées chargés avec succès !")
39
 
40
  # 📌 Récupération des chunks les plus pertinents
41
  def retrieve_relevant_chunks(question, k=5):
 
42
  question_embedding_response = mistral_client.embeddings.create(
43
  model=model_embedding,
44
  inputs=[question],
45
  )
46
  question_embedding = np.array(question_embedding_response.data[0].embedding).astype('float32').reshape(1, -1)
 
 
 
 
 
 
47
  distances, indices = index.search(question_embedding, k)
 
48
  if len(indices[0]) == 0:
49
  print("⚠️ Avertissement : Aucun chunk pertinent trouvé, réponse possible moins précise.")
50
+ return [], []
 
51
  return [chunked_docs[i] for i in indices[0]]
52
  #endregion
53
 
54
  #region# Définition des prompts
55
+ def generate_prompts(score:str, type: str, annee_min: str, annee_max:str, context) -> dict:
56
  """
57
  Genere les prefixes et suffixes des prompts pour Mistral en fonction du score de vulgarisation, du type d'espece, et les années des documents
58
  Args:
 
72
 
73
  if score == "1":
74
  prefix_prompt = f"""Tu es un assistant IA spécialisé en nutrition de la volaille. Ton utilisateur est un chercheur travaillant sur
75
+ l'amélioration des régimes alimentaires pour optimiser la santé et la croissance des {type_description}. Voici les informations extraites des documents à utiliser avec priorité : {context}.
76
  Réponds en vulgarisant les informations.
77
  Pour fournir la réponse, tu dois te baser sur des publications/articles qui ont une date de publication entre {annee_min} et {annee_max}."""
78
  suffix_prompt = """Réponds en français et donne une réponse directe et claire.
79
  Fini par faire une bibliographie avec les références bibliographiquesque tu as utilisé."""
80
  elif score == "2":
81
  prefix_prompt = f"""Tu es un assistant IA spécialisé en nutrition de la volaille. Ton utilisateur est un chercheur travaillant sur
82
+ l'amélioration des régimes alimentaires pour optimiser la santé et la croissance des {type_description}. Voici les informations extraites des documents à utiliser avec priorité : {context}.
83
  Réponds en fournissant des explications claires et concises, adaptées à la question posée.
84
  Pour fournir la réponse, tu dois te baser sur des publications/articles qui ont une date de publication entre {annee_min} et {annee_max}.
85
  Tes réponses doivent être structurées, complètes et adaptées aux professionnels du secteur."""
 
89
  Fini par faire une bibliographie avec les références bibliographiques que tu as utilisé."""
90
  elif score == "3":
91
  prefix_prompt = f"""Tu es un assistant IA spécialisé en nutrition de la volaille. Ton utilisateur est un chercheur travaillant sur
92
+ l'amélioration des régimes alimentaires pour optimiser la santé et la croissance des {type_description}. Voici les informations extraites des documents à utiliser avec priorité : {context}.
93
  Réponds en fournissant des explications détaillées et précises, adaptées à la complexité de la question posée.
94
  N'oublie pas de citer à la fin de ta réponse les références sur lesquelles tu t'es basé avec son année (entre {annee_min} et {annee_max}).
95
  Tes réponses doivent être structurées, complètes et adaptées aux professionnels du secteur."""
 
264
 
265
  #Années de publication
266
  choix_annee = st.sidebar.slider("Années de publication",
267
+ min_value=1980,
268
  max_value=2025,
269
+ value=(2010,2025))
270
  #endregion
271
 
272
  #region# Interface utilisateur
 
279
 
280
  #todo mettre relevant chunks et context =
281
  relevant_chunks= retrieve_relevant_chunks(user_input)
282
+ # context = "\n".join([chunk["text"] for chunk in relevant_chunks])
283
+ chunk_references = [f"[{i+1}]" for i in range(len(relevant_chunks))]
284
+ context = "\n\n".join([f"{chunk_references[i]} (Source: {src['metadata']['source']}) :\n{src['text']}" for i, src in enumerate(relevant_chunks)])
285
 
286
  response0 = prompt_pipeline(
287
  user_prompt = user_input,
 
312
  </div>
313
  """, unsafe_allow_html=True)
314
 
315
+ #print du contexte
316
+ st.subheader("Sources :")
317
+ st.markdown(f"""
318
+ <div style="border: 2px solid #453103; padding: 15px; border-radius: 10px;">
319
+ {context}
320
+ </div>
321
+ """, unsafe_allow_html=True)
322
+
323
+ #réponse sans contexte
324
  response1 = prompt_pipeline(
325
  user_prompt = user_input,
326
  niveau_detail=choix_vulgarisation,
 
336
  {response1['reponse_propre']}
337
  </div>
338
  """, unsafe_allow_html=True)
339
+
340
  #encadré sources
341
  # # Afficher un titre
342
  # st.subheader("Sources :")