MySafeCode's picture
Rename a.py to aa.py
b0593c4 verified
import os
import time
import gradio as gr
import tempfile
import requests
from byteplussdkarkruntime import Ark
from PIL import Image
import io
# Get API key from Hugging Face secret "Key"
API_KEY = os.environ.get("Key", "")
# Initialize client exactly like your working code
client = Ark(
base_url="https://ark.ap-southeast.bytepluses.com/api/v3",
api_key=API_KEY,
)
def upload_image_to_temp_url(image):
"""Upload image to temporary hosting and return URL"""
# For now, we need a public URL for the API
# Option 1: Use a free image hosting service
# Option 2: Save temporarily and return path (won't work for API)
# Option 3: Keep URL input for now with preview
# Let's keep it simple - return None and we'll handle it in the UI
return None
def generate_video(image, prompt_text, progress=gr.Progress()):
"""Generate video using your exact working code pattern"""
if not API_KEY:
yield "❌ API Key not configured. Please add 'Key' secret.", None
return
if image is None:
yield "⚠️ Please upload an image first", None
return
try:
progress(0, desc="Preparing image...")
# Save uploaded image temporarily
with tempfile.NamedTemporaryFile(suffix=".png", delete=False) as tmp_file:
image.save(tmp_file.name)
# Upload to a temporary hosting service
# For now, we'll use a placeholder - we need to implement this
# Option: Use imgbb.com API or similar
image_url = "https://ark-doc.tos-ap-southeast-1.bytepluses.com/seepro_i2v%20.png" # Placeholder
# TODO: Implement actual image upload to hosting service
yield "⏳ Note: Direct image upload needs hosting service. Using placeholder for now.", None
time.sleep(1)
progress(0.2, desc="Creating request...")
# Exactly your working code structure
print("----- create request -----")
create_result = client.content_generation.tasks.create(
model="seedance-1-5-pro-251215",
content=[
{
"type": "text",
"text": prompt_text
},
{
"type": "image_url",
"image_url": {
"url": image_url
}
}
]
)
task_id = create_result.id
print(f"Task created: {task_id}")
yield f"✅ Task created: {task_id}", None
progress(0.3, desc="Polling for results...")
# Polling exactly like your working code
attempts = 0
max_attempts = 120 # 2 minutes max
while attempts < max_attempts:
get_result = client.content_generation.tasks.get(task_id=task_id)
status = get_result.status
if status == "succeeded":
progress(1.0, desc="Complete!")
# Extract video URL from the response structure we saw
video_url = get_result.content.video_url if hasattr(get_result, 'content') else None
print(f"Video URL: {video_url}")
yield "✅ Video generated successfully!", video_url
return
elif status == "failed":
error_msg = get_result.error if hasattr(get_result, 'error') else "Unknown error"
yield f"❌ Failed: {error_msg}", None
return
else:
progress(0.3 + (attempts/max_attempts)*0.7, desc=f"Status: {status}")
yield f"⏳ Status: {status}... (attempt {attempts + 1})", None
time.sleep(1)
attempts += 1
yield "⏰ Timeout after 2 minutes", None
except Exception as e:
print(f"Error: {e}")
yield f"❌ Error: {str(e)}", None
# Simple, clean interface
with gr.Blocks(title="BytePlus Video Generator", theme=gr.themes.Soft()) as demo:
gr.Markdown("""
# 🎥 BytePlus Video Generator
Upload an image and describe the video you want to generate.
""")
# Show API key status
if API_KEY:
gr.Markdown("✅ **API Key:** Configured")
else:
gr.Markdown("❌ **API Key:** Not configured - please add 'Key' secret")
with gr.Row():
with gr.Column():
# Image upload
image_input = gr.Image(
label="Upload Starting Image",
type="pil",
height=300
)
# Text prompt
prompt = gr.Textbox(
label="Video Description",
lines=4,
placeholder="Describe what you want to see...",
value="At breakneck speed, drones thread through intricate obstacles or stunning natural wonders, delivering an immersive, heart-pounding flying experience. --duration 5 --camerafixed false"
)
# Generate button
generate_btn = gr.Button("🚀 Generate Video", variant="primary", size="lg")
with gr.Column():
# Status
status = gr.Textbox(
label="Status",
lines=4,
interactive=False
)
# Video output
video_output = gr.Video(
label="Generated Video",
interactive=False
)
# Example prompts
gr.Markdown("---")
gr.Markdown("### Example Prompts")
with gr.Row():
gr.Button("Nature").click(
fn=lambda: "Aerial drone shot over mountains at sunrise, cinematic --duration 5 --camerafixed false",
outputs=prompt
)
gr.Button("City").click(
fn=lambda: "Fast drone racing through futuristic city streets --duration 5 --camerafixed false",
outputs=prompt
)
gr.Button("Ocean").click(
fn=lambda: "Drone following waves at golden hour --duration 5 --camerafixed false",
outputs=prompt
)
# Connect the generate button
generate_event = generate_btn.click(
fn=generate_video,
inputs=[image_input, prompt],
outputs=[status, video_output]
)
if __name__ == "__main__":
demo.launch(server_name="0.0.0.0")