tc043 commited on
Commit
f156e8b
·
1 Parent(s): ef6005f

fix: improve semantic overlap validation, strip task prefixes, and refine fallback prompts

Browse files
Files changed (1) hide show
  1. app.py +50 -6
app.py CHANGED
@@ -133,15 +133,41 @@ def append_history(state, displayed_task: str, raw_task: str) -> None:
133
  def is_semantic_repeat(new_task: str, history: list) -> bool:
134
  if not history:
135
  return False
136
- new_words = set(new_task.lower().split())
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
137
  if not new_words:
138
  return False
 
139
  for past in history[-3:]:
140
- past_words = set(past.lower().split())
141
  if not past_words:
142
  continue
143
  overlap = len(new_words & past_words) / max(len(new_words | past_words), 1)
144
- if overlap > 0.7: # 70% word overlap = semantic repeat
145
  return True
146
  return False
147
 
@@ -159,6 +185,21 @@ def clean_and_validate_task(raw_output: str, history: list, skipped_history: lis
159
  if not cleaned:
160
  return "", False
161
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
162
  # Check for prompt leakage and scaffolding words
163
  invalid_keywords = [
164
  "completed tasks", "failures", "system", "user", "assistant",
@@ -251,14 +292,17 @@ async def generate_atomic_task(goal: str, previous_failures: int, history: list
251
 
252
  user_content = f"Goal: {goal}\nCompleted Tasks: {history_str}\nFailures: {previous_failures}\n"
253
  if last_skipped:
254
- user_content += f"CRITICAL: The user explicitly skipped '{last_skipped}'. Do NOT output it again. Generate an ALTERNATIVE physical starting action.\n"
 
 
 
255
  elif last_task:
256
- user_content += f"CRITICAL: Do NOT output '{last_task}'. Output the strictly NEXT new physical step.\n"
257
  else:
258
  user_content += "Output the NEXT step.\n"
259
 
260
  messages = [
261
- {"role": "system", "content": "You are a cognitive pacemaker. Focus strictly on the physical goal and break it down into an extremely tiny, atomic physical action under 8 words. Ignore mental blocks or feelings of being stuck and output ONLY the single physical action step."},
262
  {"role": "user", "content": user_content}
263
  ]
264
  fallback_res = await run_minicpm(
 
133
  def is_semantic_repeat(new_task: str, history: list) -> bool:
134
  if not history:
135
  return False
136
+
137
+ stop_words = {"i", "need", "to", "a", "the", "an", "and", "or", "but", "with", "for", "of", "on", "at", "by", "start", "with"}
138
+
139
+ def get_stems(task_str):
140
+ words = task_str.lower().split()
141
+ stems = []
142
+ for w in words:
143
+ w = w.strip(".,!?\"'();:")
144
+ if w in stop_words or not w:
145
+ continue
146
+ # Simple suffix stemming
147
+ if len(w) > 4:
148
+ if w.endswith("ing"):
149
+ w = w[:-3]
150
+ elif w.endswith("ies"):
151
+ w = w[:-3] + "y"
152
+ elif w.endswith("es"):
153
+ w = w[:-2]
154
+ elif w.endswith("ed"):
155
+ w = w[:-2]
156
+ elif w.endswith("s") and not w.endswith("ss"):
157
+ w = w[:-1]
158
+ stems.append(w)
159
+ return set(stems)
160
+
161
+ new_words = get_stems(new_task)
162
  if not new_words:
163
  return False
164
+
165
  for past in history[-3:]:
166
+ past_words = get_stems(past)
167
  if not past_words:
168
  continue
169
  overlap = len(new_words & past_words) / max(len(new_words | past_words), 1)
170
+ if overlap > 0.6: # 60% overlap on key word stems = semantic repeat
171
  return True
172
  return False
173
 
 
185
  if not cleaned:
186
  return "", False
187
 
188
+ # Strip conversational prefixes
189
+ prefixes_to_strip = [
190
+ "i need to ", "i should ", "i have to ", "let's ", "we should ",
191
+ "please ", "you need to ", "you should "
192
+ ]
193
+ cleaned_lower = cleaned.lower()
194
+ for prefix in prefixes_to_strip:
195
+ if cleaned_lower.startswith(prefix):
196
+ cleaned = cleaned[len(prefix):]
197
+ cleaned_lower = cleaned.lower()
198
+
199
+ # Capitalize the first letter again
200
+ if cleaned:
201
+ cleaned = cleaned[0].upper() + cleaned[1:]
202
+
203
  # Check for prompt leakage and scaffolding words
204
  invalid_keywords = [
205
  "completed tasks", "failures", "system", "user", "assistant",
 
292
 
293
  user_content = f"Goal: {goal}\nCompleted Tasks: {history_str}\nFailures: {previous_failures}\n"
294
  if last_skipped:
295
+ user_content += (
296
+ f"CRITICAL: The user explicitly skipped '{last_skipped}'. Do NOT output it again. "
297
+ f"Stay on the current sub-topic or context of the last step, but generate an ALTERNATIVE physical starting action."
298
+ )
299
  elif last_task:
300
+ user_content += f"CRITICAL: Do NOT output '{last_task}'. Stay on the same sub-topic or context, but output the strictly NEXT new physical step.\n"
301
  else:
302
  user_content += "Output the NEXT step.\n"
303
 
304
  messages = [
305
+ {"role": "system", "content": "You are a cognitive pacemaker. Focus strictly on the physical goal and break it down into an extremely tiny, atomic physical action under 8 words. Stay contextually coherent with the user's completed tasks, do NOT jump to unrelated sub-tasks, and output ONLY the single physical action step."},
306
  {"role": "user", "content": user_content}
307
  ]
308
  fallback_res = await run_minicpm(