Angshul commited on
Commit
0b72dc4
·
verified ·
1 Parent(s): 1dc8114

Upload app.py

Browse files
Files changed (1) hide show
  1. app.py +68 -0
app.py ADDED
@@ -0,0 +1,68 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ """Hugging Face Space: live CPU demo for the exact fixed evidence-graph reranker."""
2
+ import json
3
+ import gradio as gr
4
+
5
+ # ZeroGPU requires an actual GPU-marked Gradio event function at startup.
6
+ # The reranker remains CPU-only; the decorator is needed for ZeroGPU hosting.
7
+ # On ordinary CPU installations the shim leaves the function unchanged.
8
+ try:
9
+ import spaces
10
+ except ImportError:
11
+ class _LocalSpaces:
12
+ @staticmethod
13
+ def GPU(*args, **kwargs):
14
+ if args and callable(args[0]):
15
+ return args[0]
16
+ return lambda fn: fn
17
+ spaces = _LocalSpaces()
18
+ from evidence_graph_reranker import EvidenceGraphReranker
19
+
20
+ _RERANKERS = {}
21
+ EXAMPLE = [
22
+ {"title": "Atlas device", "text": "The Atlas device was launched by Novus Labs in 2025."},
23
+ {"title": "Novus Labs", "text": "Novus Labs was founded by Mira Chen in 2018."},
24
+ {"title": "Orion spacecraft", "text": "The Orion spacecraft is designed for space missions."},
25
+ {"title": "Electronics", "text": "Electronics can be manufactured in many countries."},
26
+ ]
27
+
28
+
29
+ @spaces.GPU(duration=120)
30
+ def demo(query, passages_json, budget, backend):
31
+ try:
32
+ docs = json.loads(passages_json)
33
+ if not isinstance(docs, list) or not 1 <= len(docs) <= 100:
34
+ raise ValueError("Enter a JSON list containing 1–100 passages.")
35
+ if not query.strip():
36
+ raise ValueError("Query cannot be empty.")
37
+ if backend not in _RERANKERS:
38
+ _RERANKERS[backend] = EvidenceGraphReranker(backend=backend, device="cpu", batch_size=16)
39
+ ranked = _RERANKERS[backend].rank(query, docs, k=int(budget))
40
+ table = [
41
+ [i + 1, r["index"], r["title"] or "(untitled)",
42
+ round(r["relevance_score"], 4), round(r["step_score"], 4),
43
+ round(r["directed_link_bonus"], 2)]
44
+ for i, r in enumerate(ranked)
45
+ ]
46
+ return table, json.dumps(ranked, indent=2, ensure_ascii=False)
47
+ except Exception as exc:
48
+ return [], json.dumps({"error": str(exc)})
49
+
50
+ with gr.Blocks(title="Evidence-Graph Reranker") as app:
51
+ gr.Markdown("# Evidence-Graph Reranker\nTraining-free, query-conditioned **joint evidence selection** after neural relevance scoring.\n\nA passage's usefulness can rise when it completes a link from a previously selected passage. This demo uses **one fixed graph rule** for every dataset. Model weights are fetched from their original Hugging Face repositories.")
52
+ query = gr.Textbox(label="Query", value="Who founded the company that released the Atlas device?")
53
+ passages = gr.Code(label="Candidate passages (JSON array; optional title)", language="json",
54
+ value=json.dumps(EXAMPLE, indent=2))
55
+ with gr.Row():
56
+ budget = gr.Slider(minimum=1, maximum=10, step=1, value=3, label="Passage budget (k)")
57
+ backend = gr.Dropdown(choices=["cross-encoder", "dense"], value="cross-encoder",
58
+ label="Pretrained neural relevance model")
59
+ go = gr.Button("Select complementary evidence", variant="primary")
60
+ table = gr.Dataframe(headers=["Rank", "Candidate index", "Title", "Neural score", "Selection score", "Link bonus"],
61
+ datatype=["number", "number", "str", "number", "number", "number"],
62
+ label="Selected passages", interactive=False)
63
+ output = gr.Code(label="Full selection JSON", language="json")
64
+ go.click(demo, inputs=[query, passages, budget, backend], outputs=[table, output])
65
+ gr.Markdown("**Interpretation:** `selection_score` is a step-dependent heuristic, not a probability. Gold labels are never used by the selector. Reported benchmarks measure complete evidence coverage, *not* LLM-generated answer accuracy. See `MODEL_CARD.md` for protocols and caveats.")
66
+
67
+ if __name__ == "__main__":
68
+ app.launch(ssr_mode=False)