jebin2 commited on
Commit
c4f61f9
·
1 Parent(s): 8dc9ae3

on demand url

Browse files
Files changed (2) hide show
  1. routers/gemini.py +54 -11
  2. services/gemini_job_worker.py +6 -23
routers/gemini.py CHANGED
@@ -325,6 +325,7 @@ async def get_job_status(
325
  """
326
  Get the status of a job.
327
  Poll this endpoint until status is 'completed' or 'failed'.
 
328
  """
329
  query = select(GeminiJob).where(
330
  GeminiJob.job_id == job_id,
@@ -339,6 +340,14 @@ async def get_job_status(
339
  detail="Job not found"
340
  )
341
 
 
 
 
 
 
 
 
 
342
  response = {
343
  "success": True,
344
  "job_id": job.job_id,
@@ -348,6 +357,10 @@ async def get_job_status(
348
  "credits_remaining": user.credits
349
  }
350
 
 
 
 
 
351
  if job.status == "queued":
352
  response["position"] = await get_queue_position(db, job.job_id)
353
 
@@ -359,7 +372,7 @@ async def get_job_status(
359
  response["output"] = job.output_data
360
 
361
  # For video jobs, add download URL
362
- if job.job_type == "video" and job.output_data and job.output_data.get("filename"):
363
  response["download_url"] = f"/gemini/download/{job.job_id}"
364
 
365
  if job.status == "failed":
@@ -377,6 +390,7 @@ async def download_video(
377
  ):
378
  """
379
  Download a generated video.
 
380
  """
381
  query = select(GeminiJob).where(
382
  GeminiJob.job_id == job_id,
@@ -392,24 +406,53 @@ async def download_video(
392
  detail="Job not found"
393
  )
394
 
395
- if job.status != "completed" or not job.output_data or not job.output_data.get("filename"):
396
  raise HTTPException(
397
  status_code=status.HTTP_400_BAD_REQUEST,
398
  detail="Video not ready for download"
399
  )
400
 
401
- filepath = os.path.join(DOWNLOADS_DIR, job.output_data["filename"])
402
- if not os.path.exists(filepath):
 
 
 
 
 
 
 
 
 
 
 
 
403
  raise HTTPException(
404
- status_code=status.HTTP_404_NOT_FOUND,
405
- detail="Video file not found"
406
  )
407
 
408
- return FileResponse(
409
- path=filepath,
410
- media_type="video/mp4",
411
- filename=f"video_{job_id}.mp4"
412
- )
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
413
 
414
 
415
  @router.post("/job/{job_id}/cancel")
 
325
  """
326
  Get the status of a job.
327
  Poll this endpoint until status is 'completed' or 'failed'.
328
+ For processing video jobs, this will check the Gemini API status and update the job.
329
  """
330
  query = select(GeminiJob).where(
331
  GeminiJob.job_id == job_id,
 
340
  detail="Job not found"
341
  )
342
 
343
+ # If job is processing and is a video job, check Gemini API status and update
344
+ if job.status == "processing" and job.job_type == "video" and job.third_party_id:
345
+ from services.gemini_job_worker import GeminiJobProcessor
346
+ processor = GeminiJobProcessor()
347
+ job = await processor.check_status(job, db)
348
+ await db.commit()
349
+ await db.refresh(job)
350
+
351
  response = {
352
  "success": True,
353
  "job_id": job.job_id,
 
357
  "credits_remaining": user.credits
358
  }
359
 
360
+ # Include prompt for video jobs
361
+ if job.job_type == "video" and job.input_data:
362
+ response["prompt"] = job.input_data.get("prompt")
363
+
364
  if job.status == "queued":
365
  response["position"] = await get_queue_position(db, job.job_id)
366
 
 
372
  response["output"] = job.output_data
373
 
374
  # For video jobs, add download URL
375
+ if job.job_type == "video" and job.output_data and (job.output_data.get("filename") or job.output_data.get("video_url")):
376
  response["download_url"] = f"/gemini/download/{job.job_id}"
377
 
378
  if job.status == "failed":
 
390
  ):
391
  """
392
  Download a generated video.
393
+ If the video hasn't been downloaded yet, downloads it from the stored URL.
394
  """
395
  query = select(GeminiJob).where(
396
  GeminiJob.job_id == job_id,
 
406
  detail="Job not found"
407
  )
408
 
409
+ if job.status != "completed" or not job.output_data:
410
  raise HTTPException(
411
  status_code=status.HTTP_400_BAD_REQUEST,
412
  detail="Video not ready for download"
413
  )
414
 
415
+ # Check if video is already downloaded
416
+ filename = job.output_data.get("filename")
417
+ if filename:
418
+ filepath = os.path.join(DOWNLOADS_DIR, filename)
419
+ if os.path.exists(filepath):
420
+ return FileResponse(
421
+ path=filepath,
422
+ media_type="video/mp4",
423
+ filename=f"video_{job_id}.mp4"
424
+ )
425
+
426
+ # Video not downloaded yet, download from stored URL
427
+ video_url = job.output_data.get("video_url")
428
+ if not video_url:
429
  raise HTTPException(
430
+ status_code=status.HTTP_400_BAD_REQUEST,
431
+ detail="No video URL available"
432
  )
433
 
434
+ # Download the video on-demand
435
+ from services.gemini_service import GeminiService
436
+ service = GeminiService() # Uses default API key
437
+
438
+ try:
439
+ filename = await service.download_video(video_url, job.job_id)
440
+
441
+ # Update job with downloaded filename
442
+ job.output_data = {**job.output_data, "filename": filename}
443
+ await db.commit()
444
+
445
+ filepath = os.path.join(DOWNLOADS_DIR, filename)
446
+ return FileResponse(
447
+ path=filepath,
448
+ media_type="video/mp4",
449
+ filename=f"video_{job_id}.mp4"
450
+ )
451
+ except Exception as e:
452
+ raise HTTPException(
453
+ status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
454
+ detail=f"Failed to download video: {str(e)}"
455
+ )
456
 
457
 
458
  @router.post("/job/{job_id}/cancel")
services/gemini_job_worker.py CHANGED
@@ -112,29 +112,12 @@ class GeminiJobProcessor(JobProcessor[GeminiJob]):
112
  if status_result.get("status") == "completed":
113
  video_url = status_result.get("video_url")
114
  if video_url:
115
- try:
116
- filename = await service.download_video(video_url, job.job_id)
117
- job.status = "completed"
118
- job.output_data = {"filename": filename}
119
- job.error_message = None # Clear any previous error
120
- success = True
121
- except Exception as download_error:
122
- # Download failed - track separately
123
- error_msg = f"Download failed: {download_error}"
124
- logger.error(f"Error downloading video for {job.job_id}: {download_error}")
125
-
126
- # Fail job after 5 download attempts (don't retry forever)
127
- if job.retry_count >= 5:
128
- job.status = "failed"
129
- job.error_message = error_msg
130
- job.completed_at = datetime.utcnow()
131
- else:
132
- # Retry
133
- job.retry_count += 1
134
- job.error_message = f"Download attempt {job.retry_count} failed: {download_error}"
135
- config = WorkerConfig.from_env()
136
- interval = get_interval_for_priority(job.priority, config)
137
- job.next_process_at = datetime.utcnow() + timedelta(seconds=interval)
138
  else:
139
  job.status = "failed"
140
  job.error_message = "No video URL returned"
 
112
  if status_result.get("status") == "completed":
113
  video_url = status_result.get("video_url")
114
  if video_url:
115
+ # Store video URL - download will happen on-demand when client requests
116
+ job.status = "completed"
117
+ job.output_data = {"video_url": video_url}
118
+ job.error_message = None # Clear any previous error
119
+ job.completed_at = datetime.utcnow()
120
+ success = True
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
121
  else:
122
  job.status = "failed"
123
  job.error_message = "No video URL returned"