lanretto commited on
Commit
5bb3c1a
Β·
verified Β·
1 Parent(s): d357114

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +106 -41
app.py CHANGED
@@ -7,6 +7,11 @@ import torch
7
  import numpy as np
8
  from transformers import AutoModelForSequenceClassification, AutoTokenizer
9
  import time
 
 
 
 
 
10
 
11
  # Configuration
12
  MODEL_NAME = "lanretto/shakespeare-authenticator" # Your model on HF Hub
@@ -17,14 +22,27 @@ This model analyzes linguistic patterns, vocabulary, and stylistic elements
17
  to determine if text was written by William Shakespeare or is a modern creation.
18
  """
19
 
20
- # Cache model loading to avoid reloading on every prediction
 
 
 
 
21
  def load_model():
22
- """Load model and tokenizer with caching"""
 
 
 
 
 
23
  print("πŸ”„ Loading model from Hugging Face Hub...")
24
  start_time = time.time()
25
 
26
  try:
27
- model = AutoModelForSequenceClassification.from_pretrained(MODEL_NAME)
 
 
 
 
28
  tokenizer = AutoTokenizer.from_pretrained(MODEL_NAME)
29
 
30
  # Set to evaluation mode
@@ -35,15 +53,31 @@ def load_model():
35
  load_time = time.time() - start_time
36
  print(f"βœ… Model loaded successfully in {load_time:.2f}s")
37
  print(f"πŸ“Š Model device: {device}")
 
38
 
39
  return model, tokenizer, device
40
 
41
  except Exception as e:
42
  print(f"❌ Error loading model: {e}")
43
- raise e
 
 
 
 
 
 
 
 
 
 
 
44
 
45
- # Load model once at startup
46
- model, tokenizer, device = load_model()
 
 
 
 
47
 
48
  def classify_shakespeare(text):
49
  """
@@ -57,6 +91,18 @@ def classify_shakespeare(text):
57
  "detailed_breakdown": None
58
  }
59
 
 
 
 
 
 
 
 
 
 
 
 
 
60
  try:
61
  # Tokenize the input text
62
  inputs = tokenizer(
@@ -112,16 +158,21 @@ def classify_shakespeare(text):
112
  def create_visual_output(result):
113
  """Create beautiful visual output for the prediction"""
114
  if result["error"]:
115
- return f"## ❌ Error\n{result['error']}"
 
 
 
 
 
116
 
117
  # Determine emoji and color based on prediction
118
  if "Authentic" in result["prediction"]:
119
  emoji = "βœ…"
120
- color = "green"
121
  explanation = "This text exhibits characteristics of authentic Shakespearean writing."
122
  else:
123
  emoji = "πŸ”„"
124
- color = "orange"
125
  explanation = "This text appears to be a modern creation or imitation."
126
 
127
  # Create confidence bar visualization
@@ -131,36 +182,44 @@ def create_visual_output(result):
131
  confidence_bars = f"""
132
  <div style="margin: 20px 0;">
133
  <div style="display: flex; justify-content: space-between; margin-bottom: 5px;">
134
- <span>Modern Creation</span>
135
- <span>{modern_score:.1f}%</span>
136
  </div>
137
- <div style="background: #e0e0e0; border-radius: 10px; height: 20px;">
138
- <div style="background: #ff6b6b; width: {modern_score}%; height: 100%; border-radius: 10px;"></div>
139
  </div>
140
 
141
  <div style="display: flex; justify-content: space-between; margin: 15px 0 5px 0;">
142
- <span>Authentic Shakespeare</span>
143
- <span>{shakespeare_score:.1f}%</span>
144
  </div>
145
- <div style="background: #e0e0e0; border-radius: 10px; height: 20px;">
146
- <div style="background: #4ecdc4; width: {shakespeare_score}%; height: 100%; border-radius: 10px;"></div>
147
  </div>
148
  </div>
149
  """
150
 
151
  output = f"""
152
- ## {emoji} Analysis Results
153
-
154
- **Prediction:** <span style="color: {color}; font-weight: bold;">{result['prediction']}</span>
155
- **Overall Confidence:** **{result['confidence']}**
156
-
157
- {explanation}
158
-
159
- ### Confidence Breakdown:
160
- {confidence_bars}
161
 
162
- ---
163
- *Powered by fine-tuned BERT β€’ [View Model on Hugging Face](https://huggingface.co/{MODEL_NAME})*
 
 
 
 
 
 
 
 
 
 
 
 
 
 
164
  """
165
 
166
  return output
@@ -169,7 +228,12 @@ def predict_shakespeare(text):
169
  """
170
  Main prediction function for Gradio interface
171
  """
 
172
  result = classify_shakespeare(text)
 
 
 
 
173
  return create_visual_output(result)
174
 
175
  # Example texts
@@ -191,11 +255,15 @@ with gr.Blocks(
191
  css="""
192
  .gradio-container {
193
  max-width: 800px !important;
 
194
  }
195
  .example-text {
196
  font-style: italic;
197
  color: #666;
198
  }
 
 
 
199
  """
200
  ) as demo:
201
 
@@ -233,7 +301,10 @@ with gr.Blocks(
233
  # Output section
234
  output = gr.HTML(
235
  label="πŸ“Š Analysis Results",
236
- value="<div style='text-align: center; color: #666; padding: 40px;'>Enter text above to see analysis results</div>"
 
 
 
237
  )
238
 
239
  # Model information
@@ -254,11 +325,6 @@ with gr.Blocks(
254
  - Works best with complete sentences or passages
255
  - More accurate with longer text samples
256
  - Designed for Early Modern English vs Contemporary English distinction
257
-
258
- **Limitations**
259
- - May struggle with very short text fragments
260
- - Performance varies with writing style and genre
261
- - Not designed for other languages or time periods
262
  """)
263
 
264
  # Event handlers
@@ -275,15 +341,14 @@ with gr.Blocks(
275
  )
276
 
277
  clear_btn.click(
278
- fn=lambda: ("", "<div style='text-align: center; color: #666; padding: 40px;'>Enter text above to see analysis results</div>"),
 
 
 
279
  inputs=[],
280
  outputs=[text_input, output]
281
  )
282
 
283
- # For Hugging Face Spaces deployment
284
  if __name__ == "__main__":
285
- demo.launch(
286
- server_name="0.0.0.0" if gr.is_space else None,
287
- share=False, # Set to True if you want public link during development
288
- show_error=True
289
- )
 
7
  import numpy as np
8
  from transformers import AutoModelForSequenceClassification, AutoTokenizer
9
  import time
10
+ import os
11
+
12
+ print("πŸš€ Starting Shakespeare Authenticator...")
13
+ print(f"πŸ“¦ PyTorch version: {torch.__version__}")
14
+ print(f"πŸ”§ CUDA available: {torch.cuda.is_available()}")
15
 
16
  # Configuration
17
  MODEL_NAME = "lanretto/shakespeare-authenticator" # Your model on HF Hub
 
22
  to determine if text was written by William Shakespeare or is a modern creation.
23
  """
24
 
25
+ # Global variables for model caching
26
+ model = None
27
+ tokenizer = None
28
+ device = None
29
+
30
  def load_model():
31
+ """Load model and tokenizer with caching and error handling"""
32
+ global model, tokenizer, device
33
+
34
+ if model is not None:
35
+ return model, tokenizer, device
36
+
37
  print("πŸ”„ Loading model from Hugging Face Hub...")
38
  start_time = time.time()
39
 
40
  try:
41
+ # Load model with explicit trust for remote code
42
+ model = AutoModelForSequenceClassification.from_pretrained(
43
+ MODEL_NAME,
44
+ trust_remote_code=True
45
+ )
46
  tokenizer = AutoTokenizer.from_pretrained(MODEL_NAME)
47
 
48
  # Set to evaluation mode
 
53
  load_time = time.time() - start_time
54
  print(f"βœ… Model loaded successfully in {load_time:.2f}s")
55
  print(f"πŸ“Š Model device: {device}")
56
+ print(f"🏷️ Model labels: {model.config.id2label}")
57
 
58
  return model, tokenizer, device
59
 
60
  except Exception as e:
61
  print(f"❌ Error loading model: {e}")
62
+ # Fallback to CPU if CUDA fails
63
+ try:
64
+ model = AutoModelForSequenceClassification.from_pretrained(MODEL_NAME)
65
+ tokenizer = AutoTokenizer.from_pretrained(MODEL_NAME)
66
+ model.eval()
67
+ device = torch.device('cpu')
68
+ model = model.to(device)
69
+ print(f"βœ… Model loaded on CPU as fallback")
70
+ return model, tokenizer, device
71
+ except Exception as e2:
72
+ print(f"❌ Complete failure loading model: {e2}")
73
+ raise e2
74
 
75
+ # Pre-load model at startup
76
+ try:
77
+ model, tokenizer, device = load_model()
78
+ print("πŸŽ‰ Model pre-loaded and ready for inference!")
79
+ except Exception as e:
80
+ print(f"⚠️ Model loading failed: {e}")
81
 
82
  def classify_shakespeare(text):
83
  """
 
91
  "detailed_breakdown": None
92
  }
93
 
94
+ # Ensure model is loaded
95
+ if model is None:
96
+ try:
97
+ load_model()
98
+ except:
99
+ return {
100
+ "error": "Model failed to load. Please refresh the page.",
101
+ "prediction": None,
102
+ "confidence": None,
103
+ "detailed_breakdown": None
104
+ }
105
+
106
  try:
107
  # Tokenize the input text
108
  inputs = tokenizer(
 
158
  def create_visual_output(result):
159
  """Create beautiful visual output for the prediction"""
160
  if result["error"]:
161
+ return f"""
162
+ <div style="text-align: center; padding: 20px; color: #d63031;">
163
+ <h3>❌ Error</h3>
164
+ <p>{result['error']}</p>
165
+ </div>
166
+ """
167
 
168
  # Determine emoji and color based on prediction
169
  if "Authentic" in result["prediction"]:
170
  emoji = "βœ…"
171
+ color = "#00b894"
172
  explanation = "This text exhibits characteristics of authentic Shakespearean writing."
173
  else:
174
  emoji = "πŸ”„"
175
+ color = "#e17055"
176
  explanation = "This text appears to be a modern creation or imitation."
177
 
178
  # Create confidence bar visualization
 
182
  confidence_bars = f"""
183
  <div style="margin: 20px 0;">
184
  <div style="display: flex; justify-content: space-between; margin-bottom: 5px;">
185
+ <span style="font-weight: 500;">Modern Creation</span>
186
+ <span style="font-weight: 600;">{modern_score:.1f}%</span>
187
  </div>
188
+ <div style="background: #e0e0e0; border-radius: 10px; height: 20px; overflow: hidden;">
189
+ <div style="background: #ff6b6b; width: {modern_score}%; height: 100%; border-radius: 10px; transition: width 0.5s ease;"></div>
190
  </div>
191
 
192
  <div style="display: flex; justify-content: space-between; margin: 15px 0 5px 0;">
193
+ <span style="font-weight: 500;">Authentic Shakespeare</span>
194
+ <span style="font-weight: 600;">{shakespeare_score:.1f}%</span>
195
  </div>
196
+ <div style="background: #e0e0e0; border-radius: 10px; height: 20px; overflow: hidden;">
197
+ <div style="background: #4ecdc4; width: {shakespeare_score}%; height: 100%; border-radius: 10px; transition: width 0.5s ease;"></div>
198
  </div>
199
  </div>
200
  """
201
 
202
  output = f"""
203
+ <div style="padding: 20px; border-radius: 10px; background: linear-gradient(135deg, #667eea 0%, #764ba2 100%); color: white;">
204
+ <h2 style="margin: 0; text-align: center;">{emoji} Analysis Results</h2>
205
+ </div>
 
 
 
 
 
 
206
 
207
+ <div style="padding: 20px;">
208
+ <div style="text-align: center; margin-bottom: 20px;">
209
+ <h3 style="color: {color}; margin: 0;">{result['prediction']}</h3>
210
+ <p style="font-size: 1.2em; font-weight: bold; margin: 10px 0;">Overall Confidence: {result['confidence']}</p>
211
+ </div>
212
+
213
+ <p style="text-align: center; color: #666; font-style: italic;">{explanation}</p>
214
+
215
+ <h4>Confidence Breakdown:</h4>
216
+ {confidence_bars}
217
+
218
+ <div style="margin-top: 20px; padding-top: 20px; border-top: 1px solid #e0e0e0; text-align: center; color: #888; font-size: 0.9em;">
219
+ Powered by fine-tuned BERT β€’
220
+ <a href="https://huggingface.co/{MODEL_NAME}" target="_blank" style="color: #667eea;">View Model on Hugging Face</a>
221
+ </div>
222
+ </div>
223
  """
224
 
225
  return output
 
228
  """
229
  Main prediction function for Gradio interface
230
  """
231
+ start_time = time.time()
232
  result = classify_shakespeare(text)
233
+ processing_time = time.time() - start_time
234
+
235
+ print(f"πŸ” Processed text ({len(text)} chars) in {processing_time:.2f}s")
236
+
237
  return create_visual_output(result)
238
 
239
  # Example texts
 
255
  css="""
256
  .gradio-container {
257
  max-width: 800px !important;
258
+ margin: 0 auto !important;
259
  }
260
  .example-text {
261
  font-style: italic;
262
  color: #666;
263
  }
264
+ footer {
265
+ display: none !important;
266
+ }
267
  """
268
  ) as demo:
269
 
 
301
  # Output section
302
  output = gr.HTML(
303
  label="πŸ“Š Analysis Results",
304
+ value="""<div style='text-align: center; color: #666; padding: 40px; border: 2px dashed #ddd; border-radius: 10px;'>
305
+ <h3>πŸ‘† Enter text to analyze</h3>
306
+ <p>Paste any text above and click "Analyze Text" to see if it's authentic Shakespeare!</p>
307
+ </div>"""
308
  )
309
 
310
  # Model information
 
325
  - Works best with complete sentences or passages
326
  - More accurate with longer text samples
327
  - Designed for Early Modern English vs Contemporary English distinction
 
 
 
 
 
328
  """)
329
 
330
  # Event handlers
 
341
  )
342
 
343
  clear_btn.click(
344
+ fn=lambda: ("", """<div style='text-align: center; color: #666; padding: 40px; border: 2px dashed #ddd; border-radius: 10px;'>
345
+ <h3>πŸ‘† Enter text to analyze</h3>
346
+ <p>Paste any text above and click "Analyze Text" to see if it's authentic Shakespeare!</p>
347
+ </div>"""),
348
  inputs=[],
349
  outputs=[text_input, output]
350
  )
351
 
352
+ # Launch the application - SIMPLIFIED FOR SPACES
353
  if __name__ == "__main__":
354
+ demo.launch()