esab commited on
Commit
d7ddcbf
·
verified ·
1 Parent(s): ea5c859

Fix build: bump gradio 5.5.0 -> 6.26.0, migrate to google-genai, drop asyncio pin

Browse files
Files changed (4) hide show
  1. README.md +1 -1
  2. __pycache__/app.cpython-310.pyc +0 -0
  3. app.py +107 -82
  4. requirements.txt +3 -4
README.md CHANGED
@@ -4,7 +4,7 @@ emoji: 🚀
4
  colorFrom: indigo
5
  colorTo: purple
6
  sdk: gradio
7
- sdk_version: 5.5.0
8
  app_file: app.py
9
  pinned: false
10
  license: apache-2.0
 
4
  colorFrom: indigo
5
  colorTo: purple
6
  sdk: gradio
7
+ sdk_version: 6.26.0
8
  app_file: app.py
9
  pinned: false
10
  license: apache-2.0
__pycache__/app.cpython-310.pyc ADDED
Binary file (3.92 kB). View file
 
app.py CHANGED
@@ -1,117 +1,142 @@
1
  import os
2
- import gradio as gr
3
- import google.generativeai as genai
4
  import re
5
  import asyncio
6
- from langdetect import detect
7
 
8
- # Configure Gemini AI
9
- api_key = os.getenv("GEMINI_API") # Fetch the Gemini API key securely
10
- genai.configure(api_key=api_key)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
11
 
12
- # Define the model with desired generation configuration
13
- generation_config = {
14
  "temperature": 0.7,
15
  "top_p": 0.9,
16
  "top_k": 30,
17
  "max_output_tokens": 2500,
18
- "response_mime_type": "text/plain",
19
  }
20
- model_name = "gemini-1.5-flash" # Use the updated model
 
 
 
 
 
 
21
 
22
  instructions = {
23
- "es" : (
24
- "Eres un tutor experto que responde exclusivamente en castellano o catalán. "
25
- "Tus respuestas deben centrarse únicamente en temas de estadística básica y "
26
- "todo el código proporcionado debe implementarse exclusivamente en R."
 
27
  ),
28
  "ca": (
29
- "Ets un tutor expert que respon exclusivament en catala."
30
- "Les teves respostes s'han de centrar unicament en temes d'estadistica basica i"
31
- "tot el codi proporcionat s'ha d'implementar exclusivament en R"
32
- )
 
33
  }
34
 
 
 
 
 
 
35
  def detect_language(user_input):
36
  try:
37
  lang = detect(user_input)
38
- return lang if lang in instructions else "es" # Default to Spanish if unsupported
39
  except Exception:
40
- return "es" # Default to Spanish on detection failure
 
 
41
 
42
- # Function to detect inappropriate language
43
  def contains_inappropriate_language(text):
44
- inappropriate_patterns = [
45
- r"\b(joder|maleducado)\b", # Replace with actual patterns
46
- # Spanish examples: r"\b(maleducado|grosero)\b",
47
- ]
48
- for pattern in inappropriate_patterns:
49
- if re.search(pattern, text, re.IGNORECASE):
50
- return True
51
- return False
52
-
53
- # Define a custom render function for the chatbot interface
54
- def render_chat(messages):
55
- rendered = []
56
- for message in messages:
57
- role, content = message["role"], message["content"]
58
- if role == "user":
59
- rendered.append((content, None)) # User messages on the left
60
- else:
61
- rendered.append((None, content)) # Assistant messages on the right
62
- return rendered
63
-
64
- # Updated chatbot function with rendering
65
  async def chatbot_async(user_input, history, chat_session):
 
 
 
 
 
 
66
  if contains_inappropriate_language(user_input):
67
- warning = "El lenguaje inapropiado no está permitido. Por favor, formula tu pregunta de manera respetuosa."
 
 
 
68
  history.append({"role": "assistant", "content": warning})
69
- return render_chat(history), history, chat_session
70
 
71
- lang = detect_language(user_input)
72
- system_instruction = instructions[lang]
73
-
74
- if chat_session is None:
75
- chat_session = genai.GenerativeModel(
76
- model_name=model_name,
77
- generation_config=generation_config,
78
- system_instruction=system_instruction
79
- ).start_chat()
80
 
81
- response = await asyncio.to_thread(chat_session.send_message, user_input)
82
- reply = response.text
 
 
83
 
84
- history.append({"role": "user", "content": user_input})
85
  history.append({"role": "assistant", "content": reply})
 
86
 
87
- return render_chat(history), history, chat_session
88
 
89
- # Handling errors
90
- def chatbot_with_error_handling(user_input, history, chat_session):
91
- try:
92
- return asyncio.run(chatbot_async(user_input, history, chat_session))
93
- except Exception as e:
94
- error_message = f"Ha ocurrido un error: {str(e)}"
95
- history.append({"role": "assistant", "content": error_message})
96
- gradio_history = [[msg["role"], msg["content"]] for msg in history]
97
- return gradio_history, history, chat_session
98
-
99
- # User interface
100
- with gr.Blocks() as demo:
101
- gr.Markdown("# Chatbot de Estadística \nInteractúa con un tutor experto en estadística básica.")
102
-
103
- chatbot_interface = gr.Chatbot() # Gradio's Chatbot element, customized with rendering
104
- state = gr.State([]) # For chat history
105
- chat_session = gr.State(None) # For the chat session
106
 
107
- with gr.Row():
108
- txt = gr.Textbox(show_label=False, placeholder="Escribe tu pregunta aquí...")
109
- send_button = gr.Button("Enviar")
110
 
111
- txt.submit(chatbot_with_error_handling, [txt, state, chat_session], [chatbot_interface, state, chat_session])
112
- txt.submit(lambda: "", None, txt) # Clear input box
 
 
 
 
113
 
114
- send_button.click(chatbot_with_error_handling, [txt, state, chat_session], [chatbot_interface, state, chat_session])
115
- send_button.click(lambda: "", None, txt)
 
116
 
117
- demo.launch()
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
  import os
 
 
2
  import re
3
  import asyncio
 
4
 
5
+ import gradio as gr
6
+ from google import genai
7
+ from google.genai import types
8
+ from langdetect import detect, DetectorFactory
9
+
10
+ # Make language detection deterministic across restarts
11
+ DetectorFactory.seed = 0
12
+
13
+ api_key = os.getenv("GEMINI_API")
14
+ if not api_key:
15
+ raise RuntimeError(
16
+ "Falta la variable de entorno GEMINI_API. "
17
+ "Configurala como secreto del Space (Settings > Variables and secrets)."
18
+ )
19
+
20
+ client = genai.Client(api_key=api_key)
21
+
22
+ MODEL_NAME = os.getenv("GEMINI_MODEL", "gemini-2.5-flash")
23
 
24
+ GENERATION_CONFIG = {
 
25
  "temperature": 0.7,
26
  "top_p": 0.9,
27
  "top_k": 30,
28
  "max_output_tokens": 2500,
 
29
  }
30
+
31
+ # La deteccion automatica de idioma no es fiable en frases cortas sin acentos,
32
+ # asi que la instruccion pide ademas responder en el idioma que use el estudiante.
33
+ LANGUAGE_RULE = (
34
+ "Responde siempre en el mismo idioma que utilice el estudiante "
35
+ "(castellano o catalan), aunque la instruccion inicial este en otro idioma."
36
+ )
37
 
38
  instructions = {
39
+ "es": (
40
+ "Eres un tutor experto en estadistica. "
41
+ + LANGUAGE_RULE
42
+ + " Tus respuestas deben centrarse unicamente en temas de estadistica basica y "
43
+ "todo el codigo proporcionado debe implementarse exclusivamente en R."
44
  ),
45
  "ca": (
46
+ "Ets un tutor expert en estadistica. "
47
+ + LANGUAGE_RULE
48
+ + " Les teves respostes s'han de centrar unicament en temes d'estadistica basica i "
49
+ "tot el codi proporcionat s'ha d'implementar exclusivament en R."
50
+ ),
51
  }
52
 
53
+ INAPPROPRIATE_PATTERNS = [
54
+ re.compile(r"\b(joder|maleducado)\b", re.IGNORECASE),
55
+ ]
56
+
57
+
58
  def detect_language(user_input):
59
  try:
60
  lang = detect(user_input)
 
61
  except Exception:
62
+ return "es"
63
+ return lang if lang in instructions else "es"
64
+
65
 
 
66
  def contains_inappropriate_language(text):
67
+ return any(pattern.search(text) for pattern in INAPPROPRIATE_PATTERNS)
68
+
69
+
70
+ def create_chat_session(system_instruction):
71
+ return client.chats.create(
72
+ model=MODEL_NAME,
73
+ config=types.GenerateContentConfig(
74
+ system_instruction=system_instruction,
75
+ **GENERATION_CONFIG,
76
+ ),
77
+ )
78
+
79
+
 
 
 
 
 
 
 
 
80
  async def chatbot_async(user_input, history, chat_session):
81
+ user_input = (user_input or "").strip()
82
+ if not user_input:
83
+ return history, history, chat_session, ""
84
+
85
+ history = history + [{"role": "user", "content": user_input}]
86
+
87
  if contains_inappropriate_language(user_input):
88
+ warning = (
89
+ "El lenguaje inapropiado no esta permitido. "
90
+ "Por favor, formula tu pregunta de manera respetuosa."
91
+ )
92
  history.append({"role": "assistant", "content": warning})
93
+ return history, history, chat_session, ""
94
 
95
+ try:
96
+ if chat_session is None:
97
+ lang = detect_language(user_input)
98
+ chat_session = create_chat_session(instructions[lang])
 
 
 
 
 
99
 
100
+ response = await asyncio.to_thread(chat_session.send_message, user_input)
101
+ reply = (response.text or "").strip() or "No he podido generar una respuesta."
102
+ except Exception as exc:
103
+ reply = f"Ha ocurrido un error: {exc}"
104
 
 
105
  history.append({"role": "assistant", "content": reply})
106
+ return history, history, chat_session, ""
107
 
 
108
 
109
+ def reset_chat():
110
+ return [], [], None, ""
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
111
 
 
 
 
112
 
113
+ with gr.Blocks(title="Chatbot de Estadistica") as demo:
114
+ gr.Markdown(
115
+ "# Chatbot de Estadistica\n"
116
+ "Interactua con un tutor experto en estadistica basica. "
117
+ "El codigo de ejemplo se proporciona en R."
118
+ )
119
 
120
+ chatbot_interface = gr.Chatbot(height=450)
121
+ state = gr.State([]) # chat history in messages format
122
+ chat_session = gr.State(None) # google-genai chat session
123
 
124
+ with gr.Row():
125
+ txt = gr.Textbox(
126
+ show_label=False,
127
+ placeholder="Escribe tu pregunta aqui...",
128
+ scale=8,
129
+ autofocus=True,
130
+ )
131
+ send_button = gr.Button("Enviar", variant="primary", scale=1)
132
+ clear_button = gr.Button("Limpiar", scale=1)
133
+
134
+ inputs = [txt, state, chat_session]
135
+ outputs = [chatbot_interface, state, chat_session, txt]
136
+
137
+ txt.submit(chatbot_async, inputs, outputs)
138
+ send_button.click(chatbot_async, inputs, outputs)
139
+ clear_button.click(reset_chat, None, outputs)
140
+
141
+ if __name__ == "__main__":
142
+ demo.launch()
requirements.txt CHANGED
@@ -1,4 +1,3 @@
1
- gradio
2
- google-generativeai
3
- langdetect
4
- asyncio
 
1
+ gradio==6.26.0
2
+ google-genai>=1.0
3
+ langdetect==1.0.9