5ivatej commited on
Commit
80d39c4
·
1 Parent(s): 3fbae38

Isolate HF sessions and stabilize hosted baseline

Browse files
Files changed (2) hide show
  1. inference.py +21 -2
  2. server.py +26 -7
inference.py CHANGED
@@ -24,6 +24,7 @@ from __future__ import annotations
24
 
25
  import asyncio
26
  import os
 
27
  import sys
28
  import textwrap
29
  import traceback
@@ -179,6 +180,8 @@ def should_accept_rewrite(draft: str, candidate: str) -> bool:
179
  if not candidate:
180
  return False
181
 
 
 
182
  draft_features = extract_features(draft)
183
  candidate_features = extract_features(candidate)
184
 
@@ -186,6 +189,16 @@ def should_accept_rewrite(draft: str, candidate: str) -> bool:
186
  return False
187
  if _count_questions(candidate) > 1 or candidate_features.interrogative > 0:
188
  return False
 
 
 
 
 
 
 
 
 
 
189
 
190
  # Do not let the rewrite weaken the key stage-driving signals already
191
  # present in the deterministic draft.
@@ -199,8 +212,14 @@ def should_accept_rewrite(draft: str, candidate: str) -> bool:
199
  return False
200
  if draft_features.safety > 0 and candidate_features.safety <= 0:
201
  return False
202
-
203
- return True
 
 
 
 
 
 
204
 
205
 
206
  # -------------------------- per-task episode ---------------------------------
 
24
 
25
  import asyncio
26
  import os
27
+ import re
28
  import sys
29
  import textwrap
30
  import traceback
 
180
  if not candidate:
181
  return False
182
 
183
+ draft_norm = " ".join(re.sub(r"[^\w\s]", "", draft.lower()).split())
184
+ candidate_norm = " ".join(re.sub(r"[^\w\s]", "", candidate.lower()).split())
185
  draft_features = extract_features(draft)
186
  candidate_features = extract_features(candidate)
187
 
 
189
  return False
190
  if _count_questions(candidate) > 1 or candidate_features.interrogative > 0:
191
  return False
192
+ if len(candidate.split()) > max(24, int(len(draft.split()) * 1.2)):
193
+ return False
194
+ if draft_features.open_question != candidate_features.open_question:
195
+ return False
196
+ if draft_features.advice != candidate_features.advice:
197
+ return False
198
+ if draft_features.safety != candidate_features.safety:
199
+ return False
200
+ if draft_features.validation != candidate_features.validation:
201
+ return False
202
 
203
  # Do not let the rewrite weaken the key stage-driving signals already
204
  # present in the deterministic draft.
 
212
  return False
213
  if draft_features.safety > 0 and candidate_features.safety <= 0:
214
  return False
215
+ if draft_norm == candidate_norm:
216
+ return True
217
+
218
+ # Only accept near-verbatim rewrites; otherwise keep the proven draft.
219
+ draft_tokens = set(draft_norm.split())
220
+ candidate_tokens = set(candidate_norm.split())
221
+ overlap = len(draft_tokens & candidate_tokens) / max(1, len(draft_tokens))
222
+ return overlap >= 0.8
223
 
224
 
225
  # -------------------------- per-task episode ---------------------------------
server.py CHANGED
@@ -14,7 +14,10 @@ instances.
14
  """
15
  from __future__ import annotations
16
 
 
 
17
  from fastapi import FastAPI, HTTPException
 
18
 
19
  from src.env import ESCEnv
20
  from src.models import ResetRequest, StepRequest
@@ -29,7 +32,15 @@ app = FastAPI(
29
  ),
30
  )
31
 
32
- _env = ESCEnv()
 
 
 
 
 
 
 
 
33
 
34
 
35
  @app.get("/")
@@ -48,27 +59,35 @@ def list_tasks() -> dict:
48
 
49
 
50
  @app.post("/reset")
51
- def reset(req: ResetRequest | None = None) -> dict:
52
  req = req or ResetRequest()
 
 
 
 
 
 
 
53
  try:
54
- result = _env.reset(task_id=req.task_id, seed=req.seed)
55
  except KeyError as e:
56
  raise HTTPException(status_code=400, detail=str(e))
 
57
  return result.model_dump()
58
 
59
 
60
  @app.post("/step")
61
- def step(req: StepRequest) -> dict:
62
  try:
63
- result = _env.step(req.action)
64
  except RuntimeError as e:
65
  raise HTTPException(status_code=409, detail=str(e))
66
  return result.model_dump()
67
 
68
 
69
  @app.get("/state")
70
- def state() -> dict:
71
  try:
72
- return _env.state().model_dump()
73
  except RuntimeError as e:
74
  raise HTTPException(status_code=409, detail=str(e))
 
14
  """
15
  from __future__ import annotations
16
 
17
+ from uuid import uuid4
18
+
19
  from fastapi import FastAPI, HTTPException
20
+ from fastapi import Request, Response
21
 
22
  from src.env import ESCEnv
23
  from src.models import ResetRequest, StepRequest
 
32
  ),
33
  )
34
 
35
+ SESSION_COOKIE = "esc_session_id"
36
+ _envs: dict[str, ESCEnv] = {}
37
+
38
+
39
+ def _get_env_for_request(request: Request) -> ESCEnv:
40
+ session_id = request.cookies.get(SESSION_COOKIE)
41
+ if not session_id or session_id not in _envs:
42
+ raise RuntimeError("env.step() called before reset()")
43
+ return _envs[session_id]
44
 
45
 
46
  @app.get("/")
 
59
 
60
 
61
  @app.post("/reset")
62
+ def reset(request: Request, response: Response, req: ResetRequest | None = None) -> dict:
63
  req = req or ResetRequest()
64
+ session_id = request.cookies.get(SESSION_COOKIE)
65
+ if not session_id:
66
+ session_id = uuid4().hex
67
+ env = _envs.get(session_id)
68
+ if env is None:
69
+ env = ESCEnv()
70
+ _envs[session_id] = env
71
  try:
72
+ result = env.reset(task_id=req.task_id, seed=req.seed)
73
  except KeyError as e:
74
  raise HTTPException(status_code=400, detail=str(e))
75
+ response.set_cookie(key=SESSION_COOKIE, value=session_id, httponly=True, samesite="lax")
76
  return result.model_dump()
77
 
78
 
79
  @app.post("/step")
80
+ def step(req: StepRequest, request: Request) -> dict:
81
  try:
82
+ result = _get_env_for_request(request).step(req.action)
83
  except RuntimeError as e:
84
  raise HTTPException(status_code=409, detail=str(e))
85
  return result.model_dump()
86
 
87
 
88
  @app.get("/state")
89
+ def state(request: Request) -> dict:
90
  try:
91
+ return _get_env_for_request(request).state().model_dump()
92
  except RuntimeError as e:
93
  raise HTTPException(status_code=409, detail=str(e))