AlexDGenu commited on
Commit
4e9aecc
·
1 Parent(s): 68a9996

Refactor SmolAgent to utilize smolagents.CodeAgent and DuckDuckGoSearchTool for enhanced question answering. Update instructions and model integration, and modify requirements to include necessary packages.

Browse files
Files changed (2) hide show
  1. app.py +52 -82
  2. requirements.txt +5 -2
app.py CHANGED
@@ -1,99 +1,69 @@
1
  import os
2
  import gradio as gr
3
  import requests
4
- import inspect
5
  import pandas as pd
6
- from huggingface_hub import InferenceClient
 
 
 
 
7
 
8
- # (Keep Constants as is)
9
  # --- Constants ---
10
  DEFAULT_API_URL = "https://agents-course-unit4-scoring.hf.space"
11
  HF_TOKEN = os.getenv("HF_TOKEN")
12
- SYSTEM_PROMPT = """You are a general AI assistant. I will ask you a question. Report your thoughts, and finish your answer with the following template: FINAL ANSWER: [YOUR FINAL ANSWER]. YOUR FINAL ANSWER should be a number OR as few words as possible OR a comma separated list of numbers and/or strings. If you are asked for a number, don't use comma to write your number neither use units such as $ or percent sign unless specified otherwise. If you are asked for a string, don't use articles, neither abbreviations (e.g. for cities), and write the digits in plain text unless specified otherwise. If you are asked for a comma separated list, apply the above rules depending of whether the element to be put in the list is a number or a string."""
13
-
 
 
 
 
14
 
15
  # --- Smol Agent Definition ---
16
- # ----- THIS IS WERE YOU CAN BUILD WHAT YOU WANT ------
17
  class SmolAgent:
18
  def __init__(self, hf_token: str):
19
- print("Initializing SmolAgent...")
20
  if not hf_token:
21
- raise ValueError("Hugging Face token not found. Please set HF_TOKEN environment variable in HF Spaces settings.")
22
-
23
- self.client = InferenceClient(
24
- model="HuggingFaceTB/SmolLM-1.7B-Instruct",
 
25
  token=hf_token,
26
  )
27
- print("SmolAgent initialized with direct inference client.")
 
 
 
 
 
 
 
28
 
29
  def __call__(self, question: str) -> str:
30
  print(f"\n🪐 Running on question:\n{question}\n")
31
  try:
32
- # Use chat completion format which is more reliable
33
- messages = [
34
- {"role": "system", "content": SYSTEM_PROMPT},
35
- {"role": "user", "content": question}
36
- ]
37
-
38
- response = self.client.chat_completion(
39
- messages=messages,
40
- max_tokens=100,
41
- temperature=0.1,
42
- stop=["\n"],
43
- )
44
-
45
- # Extract the assistant's response
46
- assistant_message = response.choices[0].message.content
47
- cleaned_response = assistant_message.strip()
48
-
49
- print(f"✅ Raw model response:\n{assistant_message}\n")
50
- print(f"✅ Cleaned response to submit:\n{cleaned_response}\n")
51
-
52
- # Parse the response to extract the final answer if it follows the template
53
- if "FINAL ANSWER:" in cleaned_response:
54
- final_answer_part = cleaned_response.split("FINAL ANSWER:")[1]
55
- final_answer = final_answer_part.strip()
56
- if final_answer.startswith('[') and final_answer.endswith(']'):
57
- final_answer = final_answer[1:-1]
58
- print(f"✅ Extracted final answer: {final_answer}")
59
- return final_answer
60
- else:
61
- print(f"⚠️ No 'FINAL ANSWER:' found, returning cleaned response")
62
- return cleaned_response
63
-
64
  except Exception as e:
65
  import traceback
66
  traceback.print_exc()
67
- print(f"AGENT ERROR: {e}")
68
- # Fallback: try text_generation with different parameters
69
- try:
70
- print("🔄 Trying fallback text_generation method...")
71
- prompt = f"{SYSTEM_PROMPT}\n\nQuestion: {question}\n\nAnswer:"
72
- response = self.client.text_generation(
73
- prompt,
74
- max_new_tokens=50,
75
- temperature=0.1,
76
- do_sample=True,
77
- return_full_text=False,
78
- )
79
- cleaned_response = response.strip()
80
- print(f"✅ Fallback response: {cleaned_response}")
81
- return cleaned_response
82
- except Exception as fallback_error:
83
- print(f"❌ Fallback also failed: {fallback_error}")
84
- return f"AGENT ERROR: {e}"
85
 
86
 
87
- def run_and_submit_all( profile: gr.OAuthProfile | None):
88
  """
89
- Fetches all questions, runs the BasicAgent on them, submits all answers,
90
  and displays the results.
91
  """
92
  # --- Determine HF Space Runtime URL and Repo URL ---
93
- space_id = os.getenv("SPACE_ID") # Get the SPACE_ID for sending link to the code
94
 
95
  if profile:
96
- username= f"{profile.username}"
97
  print(f"User logged in: {username}")
98
  else:
99
  print("User not logged in.")
@@ -103,15 +73,15 @@ def run_and_submit_all( profile: gr.OAuthProfile | None):
103
  questions_url = f"{api_url}/questions"
104
  submit_url = f"{api_url}/submit"
105
 
106
- # 1. Instantiate Agent ( modify this part to create your agent)
107
  try:
108
  agent = SmolAgent(hf_token=HF_TOKEN)
109
  except Exception as e:
110
  print(f"Error instantiating agent: {e}")
111
  return f"Error initializing agent: {e}", None
112
- # In the case of an app running as a hugging Face space, this link points toward your codebase ( usefull for others so please keep it public)
113
  agent_code = f"https://huggingface.co/spaces/{space_id}/tree/main"
114
- print(agent_code)
115
 
116
  # 2. Fetch Questions
117
  print(f"Fetching questions from: {questions_url}")
@@ -120,16 +90,16 @@ def run_and_submit_all( profile: gr.OAuthProfile | None):
120
  response.raise_for_status()
121
  questions_data = response.json()
122
  if not questions_data:
123
- print("Fetched questions list is empty.")
124
- return "Fetched questions list is empty or invalid format.", None
125
  print(f"Fetched {len(questions_data)} questions.")
126
  except requests.exceptions.RequestException as e:
127
  print(f"Error fetching questions: {e}")
128
  return f"Error fetching questions: {e}", None
129
  except requests.exceptions.JSONDecodeError as e:
130
- print(f"Error decoding JSON response from questions endpoint: {e}")
131
- print(f"Response text: {response.text[:500]}")
132
- return f"Error decoding server response for questions: {e}", None
133
  except Exception as e:
134
  print(f"An unexpected error occurred fetching questions: {e}")
135
  return f"An unexpected error occurred fetching questions: {e}", None
@@ -149,14 +119,14 @@ def run_and_submit_all( profile: gr.OAuthProfile | None):
149
  answers_payload.append({"task_id": task_id, "submitted_answer": submitted_answer})
150
  results_log.append({"Task ID": task_id, "Question": question_text, "Submitted Answer": submitted_answer})
151
  except Exception as e:
152
- print(f"Error running agent on task {task_id}: {e}")
153
- results_log.append({"Task ID": task_id, "Question": question_text, "Submitted Answer": f"AGENT ERROR: {e}"})
154
 
155
  if not answers_payload:
156
  print("Agent did not produce any answers to submit.")
157
  return "Agent did not produce any answers to submit.", pd.DataFrame(results_log)
158
 
159
- # 4. Prepare Submission
160
  submission_data = {"username": username.strip(), "agent_code": agent_code, "answers": answers_payload}
161
  status_update = f"Agent finished. Submitting {len(answers_payload)} answers for user '{username}'..."
162
  print(status_update)
@@ -212,15 +182,15 @@ with gr.Blocks() as demo:
212
  """
213
  **Instructions:**
214
 
215
- 1. This space uses SmolLM-1.7B-Instruct model with direct inference for question answering.
216
  2. Log in to your Hugging Face account using the button below. This uses your HF username for submission.
217
  3. Click 'Run Evaluation & Submit All Answers' to fetch questions, run your agent, submit answers, and see the score.
218
 
219
  ---
220
  **Model Information:**
221
- - Using: HuggingFaceTB/SmolLM-1.7B-Instruct
222
- - Framework: Direct InferenceClient (optimized for single-line answers)
223
- - No additional tools (pure reasoning)
224
 
225
  **Disclaimers:**
226
  Once clicking on the "submit button, it can take quite some time ( this is the time for the agent to go through all the questions).
@@ -262,5 +232,5 @@ if __name__ == "__main__":
262
 
263
  print("-"*(60 + len(" App Starting ")) + "\n")
264
 
265
- print("Launching Gradio Interface for Basic Agent Evaluation...")
266
  demo.launch(debug=True, share=False)
 
1
  import os
2
  import gradio as gr
3
  import requests
 
4
  import pandas as pd
5
+ from smolagents import CodeAgent, InferenceClientModel, DuckDuckGoSearchTool
6
+ from dotenv import load_dotenv
7
+
8
+ # Load environment variables
9
+ load_dotenv()
10
 
 
11
  # --- Constants ---
12
  DEFAULT_API_URL = "https://agents-course-unit4-scoring.hf.space"
13
  HF_TOKEN = os.getenv("HF_TOKEN")
14
+ INSTRUCTIONS = """Your task is to answer the user's question.
15
+ Return a number OR as few words as possible OR a comma separated list of numbers and/or strings.
16
+ - If you are asked for a number, don't use a comma to write your number, and don't use units like $ or % unless specified otherwise.
17
+ - If you are asked for a string, don't use articles or abbreviations (e.g., for cities), and write digits in plain text unless specified otherwise.
18
+ - If you are asked for a comma-separated list, apply the above rules to each element.
19
+ """
20
 
21
  # --- Smol Agent Definition ---
 
22
  class SmolAgent:
23
  def __init__(self, hf_token: str):
24
+ print("Initializing SmolAgent with smolagents...")
25
  if not hf_token:
26
+ raise ValueError("Hugging Face token not found. Please set HF_TOKEN environment variable.")
27
+
28
+ # Initialize the model
29
+ model = InferenceClientModel(
30
+ model_id="meta-llama/Meta-Llama-3-8B-Instruct",
31
  token=hf_token,
32
  )
33
+
34
+ # Initialize the agent with tools and instructions
35
+ self.agent = CodeAgent(
36
+ tools=[DuckDuckGoSearchTool()],
37
+ model=model,
38
+ instructions=INSTRUCTIONS,
39
+ )
40
+ print("SmolAgent initialized with CodeAgent and DuckDuckGoSearchTool.")
41
 
42
  def __call__(self, question: str) -> str:
43
  print(f"\n🪐 Running on question:\n{question}\n")
44
  try:
45
+ # The CodeAgent's run method returns the final answer directly
46
+ answer = self.agent.run(question)
47
+ print(f" Agent's final answer: {answer}")
48
+ return str(answer) # Ensure the output is a string
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
49
  except Exception as e:
50
  import traceback
51
  traceback.print_exc()
52
+ error_message = f"AGENT ERROR: {e}"
53
+ print(f"❌ {error_message}")
54
+ return error_message
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
55
 
56
 
57
+ def run_and_submit_all(profile: gr.OAuthProfile | None):
58
  """
59
+ Fetches all questions, runs the SmolAgent on them, submits all answers,
60
  and displays the results.
61
  """
62
  # --- Determine HF Space Runtime URL and Repo URL ---
63
+ space_id = os.getenv("SPACE_ID")
64
 
65
  if profile:
66
+ username = f"{profile.username}"
67
  print(f"User logged in: {username}")
68
  else:
69
  print("User not logged in.")
 
73
  questions_url = f"{api_url}/questions"
74
  submit_url = f"{api_url}/submit"
75
 
76
+ # 1. Instantiate Agent
77
  try:
78
  agent = SmolAgent(hf_token=HF_TOKEN)
79
  except Exception as e:
80
  print(f"Error instantiating agent: {e}")
81
  return f"Error initializing agent: {e}", None
82
+
83
  agent_code = f"https://huggingface.co/spaces/{space_id}/tree/main"
84
+ print(f"Agent code link: {agent_code}")
85
 
86
  # 2. Fetch Questions
87
  print(f"Fetching questions from: {questions_url}")
 
90
  response.raise_for_status()
91
  questions_data = response.json()
92
  if not questions_data:
93
+ print("Fetched questions list is empty.")
94
+ return "Fetched questions list is empty or invalid format.", None
95
  print(f"Fetched {len(questions_data)} questions.")
96
  except requests.exceptions.RequestException as e:
97
  print(f"Error fetching questions: {e}")
98
  return f"Error fetching questions: {e}", None
99
  except requests.exceptions.JSONDecodeError as e:
100
+ print(f"Error decoding JSON response from questions endpoint: {e}")
101
+ print(f"Response text: {response.text[:500]}")
102
+ return f"Error decoding server response for questions: {e}", None
103
  except Exception as e:
104
  print(f"An unexpected error occurred fetching questions: {e}")
105
  return f"An unexpected error occurred fetching questions: {e}", None
 
119
  answers_payload.append({"task_id": task_id, "submitted_answer": submitted_answer})
120
  results_log.append({"Task ID": task_id, "Question": question_text, "Submitted Answer": submitted_answer})
121
  except Exception as e:
122
+ print(f"Error running agent on task {task_id}: {e}")
123
+ results_log.append({"Task ID": task_id, "Question": question_text, "Submitted Answer": f"AGENT ERROR: {e}"})
124
 
125
  if not answers_payload:
126
  print("Agent did not produce any answers to submit.")
127
  return "Agent did not produce any answers to submit.", pd.DataFrame(results_log)
128
 
129
+ # 4. Prepare Submission
130
  submission_data = {"username": username.strip(), "agent_code": agent_code, "answers": answers_payload}
131
  status_update = f"Agent finished. Submitting {len(answers_payload)} answers for user '{username}'..."
132
  print(status_update)
 
182
  """
183
  **Instructions:**
184
 
185
+ 1. This space uses a `smolagents.CodeAgent` with the `meta-llama/Meta-Llama-3-8B-Instruct` model.
186
  2. Log in to your Hugging Face account using the button below. This uses your HF username for submission.
187
  3. Click 'Run Evaluation & Submit All Answers' to fetch questions, run your agent, submit answers, and see the score.
188
 
189
  ---
190
  **Model Information:**
191
+ - Agent: `smolagents.CodeAgent`
192
+ - Model: `meta-llama/Meta-Llama-3-8B-Instruct`
193
+ - Tools: `DuckDuckGoSearchTool`
194
 
195
  **Disclaimers:**
196
  Once clicking on the "submit button, it can take quite some time ( this is the time for the agent to go through all the questions).
 
232
 
233
  print("-"*(60 + len(" App Starting ")) + "\n")
234
 
235
+ print("Launching Gradio Interface for Smol Agent Evaluation...")
236
  demo.launch(debug=True, share=False)
requirements.txt CHANGED
@@ -1,4 +1,7 @@
1
- huggingface_hub
2
  gradio
 
3
  requests
4
- pandas
 
 
 
1
+ -e git+https://github.com/huggingface/transformers.git
2
  gradio
3
+ python-dotenv
4
  requests
5
+ pandas
6
+ smolagents[toolkit]
7
+ huggingface_hub