Spaces:
Sleeping
Sleeping
import gradio as gr | |
import requests | |
from bs4 import BeautifulSoup | |
import google.generativeai as genai | |
def fetch_article_content(url): | |
"""Fetch article content with basic error handling""" | |
try: | |
headers = {'User-Agent': 'Mozilla/5.0'} | |
response = requests.get(url, headers=headers, timeout=8) | |
response.raise_for_status() | |
soup = BeautifulSoup(response.text, 'html.parser') | |
# Extract first 8 paragraphs | |
paragraphs = soup.find_all('p')[:8] | |
content = ' '.join([p.get_text(strip=True) for p in paragraphs]) | |
return content[:2000] # Keep it concise | |
except Exception as e: | |
return f"FETCH_ERROR: {str(e)}" | |
def generate_platform_post(article_text, api_key): | |
"""Generate post using user-provided API key""" | |
try: | |
# Configure Gemini with user's API key | |
genai.configure(api_key=api_key) | |
model = genai.GenerativeModel('gemini-1.5-pro') | |
prompt = f""" | |
Create a Reddit/Quora-style post from this article: | |
{article_text} | |
Output format: | |
Title: [short title] | |
Post: [clean HTML with 1 image tag + alt text] | |
Requirements: | |
- Title < 100 characters | |
- Include <img> with descriptive alt text | |
- Minimal styling | |
- Mobile-friendly | |
""" | |
response = model.generate_content(prompt) # Removed invalid timeout | |
return parse_gemini_response(response.text) | |
except Exception as e: | |
return ("AI ERROR", f"<p>API Error: {str(e)}</p>") | |
def parse_gemini_response(response): | |
"""Robust response parsing β returns two values (title, content)""" | |
try: | |
title = response.split("Title:")[1].split("Post:")[0].strip()[:100] | |
content = response.split("Post:")[1].strip() | |
return title, content | |
except: | |
return ("Formatting Error", "<p>Failed to parse AI response</p>") | |
def process_url(url, api_key): | |
"""Main processing pipeline with status updates""" | |
if not api_key or len(api_key.strip()) < 30: | |
yield ("API Key Required", "<p>Please enter your Gemini API key above</p>") | |
return | |
if not url.startswith("http"): | |
yield ("Invalid URL", "<p>Please enter a valid article URL</p>") | |
return | |
yield ("Fetching Article...", "<p>Connecting to URL...</p>") | |
article_text = fetch_article_content(url) | |
if article_text.startswith("FETCH_ERROR:"): | |
yield ("Fetch Failed", f"<p>{article_text.replace('FETCH_ERROR: ', '')}</p>") | |
return | |
yield ("Generating Post...", "<p>Creating content with Gemini...</p>") | |
result = generate_platform_post(article_text, api_key) | |
yield result # This will now return (title, content) | |
# Create Gradio interface | |
url_input = gr.Textbox(label="Article URL", placeholder="https://example.com/article...") | |
api_key_input = gr.Textbox( | |
label="Gemini API Key", | |
placeholder="AIzaXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX", | |
type="password" | |
) | |
title_output = gr.Textbox(label="Generated Title") | |
content_output = gr.HTML(label="Formatted Post") | |
app = gr.Interface( | |
fn=process_url, | |
inputs=[url_input, api_key_input], | |
outputs=[ | |
gr.Textbox(label="Generated Title"), | |
gr.HTML(label="Formatted Post") | |
], | |
examples=[ | |
["https://google.com", "AIzaXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"] | |
], | |
title="Article to Reddit/Quora Post Converter", | |
description="Convert news articles into optimized posts with AI-generated formatting and image descriptions", | |
allow_flagging="never", | |
live=False, | |
theme="default" | |
) | |
if __name__ == "__main__": | |
app.launch() |