urchade commited on
Commit
b9f8bd7
Β·
verified Β·
1 Parent(s): 5c4e9a7

Upload 2 files

Browse files
Files changed (2) hide show
  1. app.py +184 -0
  2. requirements.txt +1 -0
app.py ADDED
@@ -0,0 +1,184 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import gradio as gr
2
+ import json
3
+ from gliner2 import GLiNER2
4
+ from huggingface_hub import login
5
+ import os
6
+
7
+ # Get API key from environment variable
8
+ hf_token = os.getenv("HF_TOKEN")
9
+
10
+ # Authenticate with Hugging Face
11
+ login(hf_token)
12
+
13
+ # β€”β€”β€” Load model once β€”β€”β€”
14
+ model = GLiNER2.from_pretrained("fastino/gliner2-base-0207")
15
+
16
+ def run_ner(text, types_csv, descs):
17
+ types = [t.strip() for t in types_csv.split(",") if t.strip()]
18
+ desc_map = {k: v for line in descs.split("\n") if ":" in line for k,v in [line.split(":",1)]}
19
+ inp = desc_map if desc_map else types
20
+ res = model.extract_entities(text=text, entity_types=inp, include_confidence=True)
21
+ return model.pretty_print_results(res, include_confidence=True)
22
+
23
+ def run_class(text, task, labels_csv, descs, multi):
24
+ labels = [l.strip() for l in labels_csv.split(",") if l.strip()]
25
+ desc_map = {k: v for line in descs.split("\n") if ":" in line for k,v in [line.split(":",1)]}
26
+ inp = desc_map if desc_map else labels
27
+ tasks = {
28
+ task: {
29
+ "labels": list(inp.keys()) if isinstance(inp,dict) else inp,
30
+ "multi_label": multi,
31
+ **({"label_descriptions": inp} if isinstance(inp,dict) else {})
32
+ }
33
+ }
34
+ res = model.classify_text(text=text, tasks=tasks, include_confidence=True)
35
+ return model.pretty_print_results(res, include_confidence=True)
36
+
37
+ def run_struct(text, struct_json):
38
+ try:
39
+ cfg = json.loads(struct_json)
40
+ except json.JSONDecodeError as e:
41
+ return f"❌ Invalid JSON: {e}"
42
+ res = model.extract_json(text=text, structures=cfg, include_confidence=True)
43
+ return model.pretty_print_results(res, include_confidence=True)
44
+
45
+ # β€”β€”β€” Clean White Theme & Layout β€”β€”β€”
46
+ custom_css = """
47
+ body {
48
+ background: #ffffff !important;
49
+ font-family: 'Helvetica Neue', sans-serif;
50
+ color: #333333;
51
+ }
52
+ .gradio-container {
53
+ max-width: 600px;
54
+ padding: 0;
55
+ background: #ffffff;
56
+ }
57
+ header, .logo, .subtitle {
58
+ border: none !important;
59
+ box-shadow: none !important;
60
+ }
61
+ .gradio-container * {
62
+ box-shadow: none !important;
63
+ }
64
+ .card {
65
+ background: #ffffff;
66
+ padding: 15px;
67
+ }
68
+ label {
69
+ color: #444444;
70
+ font-weight: 600;
71
+ }
72
+ .gr-textbox textarea,
73
+ .gr-code,
74
+ .gr-dropdown,
75
+ .gr-checkbox,
76
+ .gr-button {
77
+ background: #ffffff !important;
78
+ box-shadow: none !important;
79
+ }
80
+ .accordion-button {
81
+ border: none !important;
82
+ box-shadow: none !important;
83
+ font-weight: 500;
84
+ }
85
+ .gr-button.primary {
86
+ background: #5b8def;
87
+ color: #ffffff;
88
+ }
89
+ """
90
+
91
+ with gr.Blocks(theme=gr.themes.Base(), css=custom_css) as demo:
92
+ # Header
93
+ gr.HTML("""
94
+ <header style="text-align:center; padding:10px 0;">
95
+ <div class="logo" style="font-size:1.8rem; font-weight:700; color:#333333;">🎯 GLiNER2</div>
96
+ <div class="subtitle" style="font-size:0.85rem; color:#777777;">Compact β€’ White Theme β€’ Screenshot-Ready</div>
97
+ </header>
98
+ """)
99
+
100
+ with gr.Tabs():
101
+ # Structure Extraction Tab
102
+ with gr.TabItem("Hierarchical Structure Extraction"):
103
+ with gr.Row(elem_classes="card"):
104
+ with gr.Column(scale=2):
105
+ txt3 = gr.Textbox(
106
+ label="Input text", lines=3,
107
+ value=(
108
+ "The Acme Pro Laptop 15” features an Intel Core i7 processor, 16GB RAM, 512GB SSD, "
109
+ "and a 15.6-inch 4K display. Priced at $1,499, it offers Wi-Fi 6, Bluetooth 5.2, and "
110
+ "a backlit keyboard."
111
+ )
112
+ )
113
+ struct3 = gr.Code(
114
+ language="json", lines=7,
115
+ label = "Schema",
116
+ value=json.dumps({
117
+ "product": [
118
+ "name::str::Product name and model",
119
+ "price::str::Product cost",
120
+ "features::list::Key product features",
121
+ "category::[electronics|software|hardware]::str"
122
+ ]
123
+ }, indent=2)
124
+ )
125
+ btn3 = gr.Button("Predict", variant="primary")
126
+ with gr.Column(scale=1):
127
+ out3 = gr.Code(language="json", lines=8, label="Output")
128
+ btn3.click(run_struct, [txt3, struct3], out3)
129
+
130
+ # NER Tab
131
+ with gr.TabItem("Named Entity Recognition"):
132
+ with gr.Row(elem_classes="card"):
133
+ with gr.Column(scale=2):
134
+ txt1 = gr.Textbox(
135
+ label="Text", lines=4,
136
+ value=(
137
+ "Dr. Alice Smith, Chief Data Scientist at OpenAI, spoke at the AI Summit "
138
+ "in San Francisco on June 12, 2025, about advancements in large-scale language "
139
+ "models, ethical AI guidelines, and real-world GPT-4 Turbo applications."
140
+ )
141
+ )
142
+ types1 = gr.Textbox(label="Types (csv)", value="person, title, organization, event, location, date, topic")
143
+ with gr.Accordion("Descriptions (opt)", open=False):
144
+ desc1 = gr.Textbox(lines=4, placeholder=(
145
+ "person: Full names\n"
146
+ "title: Roles\n"
147
+ "organization: Companies\n"
148
+ "event: Conferences\n"
149
+ "location: Cities\n"
150
+ "date: Temporal expressions"
151
+ ))
152
+ btn1 = gr.Button("Predict", variant="primary")
153
+ with gr.Column(scale=1):
154
+ out1 = gr.Code(language="json", lines=8)
155
+ btn1.click(run_ner, [txt1, types1, desc1], out1)
156
+
157
+ # Classification Tab
158
+ with gr.TabItem("Text Classification"):
159
+ with gr.Row(elem_classes="card"):
160
+ with gr.Column(scale=2):
161
+ txt2 = gr.Textbox(
162
+ label="Text", lines=4,
163
+ value=(
164
+ "The Q2 2025 financial report shows a 15% revenue increase driven by cloud "
165
+ "services, offset by a 12% rise in R&D costs. Overall sentiment is cautiously "
166
+ "optimistic among stakeholders."
167
+ )
168
+ )
169
+ task2 = gr.Textbox(label="Task", value="financial_sentiment")
170
+ labs2 = gr.Textbox(label="Labels (csv)", value="positive, negative, neutral, mixed, uncertain")
171
+ with gr.Accordion("Label Descriptions (opt)", open=False):
172
+ desc2 = gr.Textbox(lines=3, placeholder=(
173
+ "positive: Favorable outcomes\n"
174
+ "negative: Concerns raised\n"
175
+ "neutral: Balanced reporting"
176
+ ))
177
+ multi2 = gr.Checkbox(label="Multi-label?", value=True)
178
+ btn2 = gr.Button("Predict", variant="primary")
179
+ with gr.Column(scale=1):
180
+ out2 = gr.Code(language="json", lines=8)
181
+ btn2.click(run_class, [txt2, task2, labs2, desc2, multi2], out2)
182
+
183
+
184
+ demo.launch(share=False, width=600, height=300)
requirements.txt ADDED
@@ -0,0 +1 @@
 
 
1
+ gliner2