CB commited on
Commit
551bc5c
·
verified ·
1 Parent(s): 38abdf3

Update streamlit_app.py

Browse files
Files changed (1) hide show
  1. streamlit_app.py +51 -38
streamlit_app.py CHANGED
@@ -1,8 +1,8 @@
1
  # streamlit_app.py
2
  import os
3
- import string
4
  import time
5
  import json
 
6
  from glob import glob
7
  from pathlib import Path
8
 
@@ -10,30 +10,41 @@ import yt_dlp
10
  import ffmpeg
11
  import streamlit as st
12
  from dotenv import load_dotenv
13
- import requests
14
 
15
  load_dotenv()
16
 
17
- # Optional Google SDK helpers
 
 
18
  try:
19
  import google.generativeai as genai
20
  from google.generativeai import upload_file, get_file
21
  GENAI = genai
22
  HAS_GENAI = True
23
  except Exception:
24
- GENAI = None
25
- HAS_GENAI = False
 
 
 
 
 
 
 
 
 
 
26
 
27
  st.set_page_config(page_title="Generate the story of videos:", layout="wide")
28
 
29
  DATA_DIR = Path("./data")
30
  DATA_DIR.mkdir(exist_ok=True)
31
 
 
32
  st.session_state.setdefault("videos", "")
33
- # default loop unchecked as requested
34
  st.session_state.setdefault("loop_video", False)
35
 
36
- # UI - Sidebar
37
  st.sidebar.header("Video Input")
38
  st.sidebar.text_input("Video URL (or local .mp4 path)", key="url", placeholder="Enter Video URL or path")
39
 
@@ -41,7 +52,6 @@ settings_exp = st.sidebar.expander("Settings", expanded=False)
41
  env_api_key = os.getenv("GOOGLE_API_KEY", "")
42
  API_KEY = settings_exp.text_input("Google API Key", value=env_api_key, placeholder="Set GOOGLE_API_KEY in .env or enter here")
43
 
44
- # Keep model_id as the short model name (e.g. "gemini-2.0-flash-lite")
45
  raw_model = settings_exp.text_input("Gemini Model (model name)", "gemini-2.0-flash-lite")
46
  model_id = raw_model.strip() or "gemini-2.0-flash-lite"
47
 
@@ -51,7 +61,7 @@ settings_exp.text_input("Video Password", key="video-password", placeholder="Ent
51
  if not API_KEY:
52
  settings_exp.warning("No Google API key provided. Uploading/processing will not work.", icon="⚠️")
53
 
54
- # Basic safety settings (kept OFF by default)
55
  safety_settings = [
56
  {"category": "HARM_CATEGORY_HARASSMENT", "threshold": "OFF"},
57
  {"category": "HARM_CATEGORY_HATE_SPEECH", "threshold": "OFF"},
@@ -59,7 +69,7 @@ safety_settings = [
59
  {"category": "HARM_CATEGORY_DANGEROUS_CONTENT", "threshold": "OFF"},
60
  ]
61
 
62
- # Utilities
63
  def sanitize_filename(path_str: str):
64
  name = Path(path_str).name
65
  name = name.lower().translate(str.maketrans("", "", string.punctuation)).replace(" ", "_")
@@ -82,7 +92,7 @@ def download_video_ytdlp(url: str, save_dir: str, video_password: str = None) ->
82
  # local file
83
  if os.path.exists(url) and os.path.isfile(url):
84
  return convert_video_to_mp4(url)
85
- outtmpl = os.path.join(save_dir, "%(id)s.%(ext)s")
86
  ydl_opts = {"outtmpl": outtmpl, "format": "best"}
87
  if video_password:
88
  ydl_opts["videopassword"] = video_password
@@ -96,7 +106,18 @@ def download_video_ytdlp(url: str, save_dir: str, video_password: str = None) ->
96
  raise FileNotFoundError("Downloaded video not found")
97
  return convert_video_to_mp4(matches[0])
98
 
99
- # Load video action
 
 
 
 
 
 
 
 
 
 
 
100
  if st.sidebar.button("Load Video", use_container_width=True):
101
  try:
102
  video_password = st.session_state.get("video-password", "")
@@ -138,13 +159,13 @@ if st.session_state["videos"]:
138
 
139
  st.sidebar.write("Title:", Path(st.session_state["videos"]).name)
140
 
141
- # Upload helpers
142
  def upload_video(filepath: str):
143
  if not API_KEY:
144
  raise RuntimeError("No API key provided")
145
  if HAS_GENAI and callable(upload_file):
146
  return upload_file(filepath)
147
- # REST upload (legacy v1beta2 upload used by file-based multimodal flows)
148
  url = "https://generative.googleapis.com/v1beta2/files?uploadType=multipart"
149
  headers = {"Authorization": f"Bearer {API_KEY}"}
150
  metadata = {"mimeType": "video/mp4", "displayName": Path(filepath).name}
@@ -182,7 +203,7 @@ def poll_file_processed(file_obj, timeout=180):
182
  raise TimeoutError("File processing timed out")
183
  time.sleep(2)
184
 
185
- # Call model (streamlined, using generativeapis host path format)
186
  def call_model_with_file(prompt_text: str, uploaded_file_obj):
187
  if not API_KEY:
188
  raise RuntimeError("No API key provided")
@@ -193,34 +214,26 @@ def call_model_with_file(prompt_text: str, uploaded_file_obj):
193
  else uploaded_file_obj.get("name") or uploaded_file_obj.get("id")
194
  )
195
 
196
- # Prefer SDK responses.generate if available
197
- if HAS_GENAI:
198
- try:
199
- if hasattr(GENAI, "responses") and hasattr(GENAI.responses, "generate"):
200
- request = {
201
- "model": f"models/{model_id}",
202
- "input": [{"text": prompt_text, "files": [{"name": file_ref_name}]}],
203
- "safetySettings": safety_settings,
204
- "maxOutputTokens": 1000,
205
- }
206
- return GENAI.responses.generate(**request)
207
- except Exception:
208
- pass
209
-
210
- # Use generativeapis.googleapis.com with correct path: /v1/models/{model}:generate
211
- endpoint = f"https://generativeapis.googleapis.com/v1/models/{model_id}:generate"
212
  body = {
213
- "input": [
214
- {
215
- "text": prompt_text,
216
- "files": [{"name": file_ref_name}],
217
- }
218
- ],
219
  "safetySettings": safety_settings,
220
  "maxOutputTokens": 1000,
221
  }
222
  headers = {"Authorization": f"Bearer {API_KEY}", "Content-Type": "application/json"}
223
-
224
  r = requests.post(endpoint, headers=headers, json=body, timeout=180)
225
  r.raise_for_status()
226
  return r.json()
 
1
  # streamlit_app.py
2
  import os
 
3
  import time
4
  import json
5
+ import string
6
  from glob import glob
7
  from pathlib import Path
8
 
 
10
  import ffmpeg
11
  import streamlit as st
12
  from dotenv import load_dotenv
 
13
 
14
  load_dotenv()
15
 
16
+ # Optional SDK imports — we'll try to import and set flags
17
+ HAS_GENAI = False
18
+ GENAI = None
19
  try:
20
  import google.generativeai as genai
21
  from google.generativeai import upload_file, get_file
22
  GENAI = genai
23
  HAS_GENAI = True
24
  except Exception:
25
+ upload_file = None
26
+ get_file = None
27
+
28
+ # Optional phi Agent (useful if phi is installed)
29
+ HAS_PHI_AGENT = False
30
+ try:
31
+ from phi.agent import Agent
32
+ from phi.model.google import Gemini
33
+ from phi.tools.duckduckgo import DuckDuckGo
34
+ HAS_PHI_AGENT = True
35
+ except Exception:
36
+ Agent = Gemini = DuckDuckGo = None
37
 
38
  st.set_page_config(page_title="Generate the story of videos:", layout="wide")
39
 
40
  DATA_DIR = Path("./data")
41
  DATA_DIR.mkdir(exist_ok=True)
42
 
43
+ # Session defaults
44
  st.session_state.setdefault("videos", "")
 
45
  st.session_state.setdefault("loop_video", False)
46
 
47
+ # Sidebar UI
48
  st.sidebar.header("Video Input")
49
  st.sidebar.text_input("Video URL (or local .mp4 path)", key="url", placeholder="Enter Video URL or path")
50
 
 
52
  env_api_key = os.getenv("GOOGLE_API_KEY", "")
53
  API_KEY = settings_exp.text_input("Google API Key", value=env_api_key, placeholder="Set GOOGLE_API_KEY in .env or enter here")
54
 
 
55
  raw_model = settings_exp.text_input("Gemini Model (model name)", "gemini-2.0-flash-lite")
56
  model_id = raw_model.strip() or "gemini-2.0-flash-lite"
57
 
 
61
  if not API_KEY:
62
  settings_exp.warning("No Google API key provided. Uploading/processing will not work.", icon="⚠️")
63
 
64
+ # Safety settings (kept OFF by default)
65
  safety_settings = [
66
  {"category": "HARM_CATEGORY_HARASSMENT", "threshold": "OFF"},
67
  {"category": "HARM_CATEGORY_HATE_SPEECH", "threshold": "OFF"},
 
69
  {"category": "HARM_CATEGORY_DANGEROUS_CONTENT", "threshold": "OFF"},
70
  ]
71
 
72
+ # Helpers
73
  def sanitize_filename(path_str: str):
74
  name = Path(path_str).name
75
  name = name.lower().translate(str.maketrans("", "", string.punctuation)).replace(" ", "_")
 
92
  # local file
93
  if os.path.exists(url) and os.path.isfile(url):
94
  return convert_video_to_mp4(url)
95
+ outtmpl = str(Path(save_dir) / "%(id)s.%(ext)s")
96
  ydl_opts = {"outtmpl": outtmpl, "format": "best"}
97
  if video_password:
98
  ydl_opts["videopassword"] = video_password
 
106
  raise FileNotFoundError("Downloaded video not found")
107
  return convert_video_to_mp4(matches[0])
108
 
109
+ # Initialize SDK if available and API key present
110
+ if API_KEY and HAS_GENAI:
111
+ try:
112
+ GENAI.configure(api_key=API_KEY)
113
+ except Exception:
114
+ # older SDK variants may use genai.configure or genai.set_api_key; try both silently
115
+ try:
116
+ GENAI.configure(api_key=API_KEY)
117
+ except Exception:
118
+ pass
119
+
120
+ # Download action
121
  if st.sidebar.button("Load Video", use_container_width=True):
122
  try:
123
  video_password = st.session_state.get("video-password", "")
 
159
 
160
  st.sidebar.write("Title:", Path(st.session_state["videos"]).name)
161
 
162
+ # Upload and polling using SDK if available, otherwise fallback to REST
163
  def upload_video(filepath: str):
164
  if not API_KEY:
165
  raise RuntimeError("No API key provided")
166
  if HAS_GENAI and callable(upload_file):
167
  return upload_file(filepath)
168
+ # REST fallback (v1beta2 files endpoint)
169
  url = "https://generative.googleapis.com/v1beta2/files?uploadType=multipart"
170
  headers = {"Authorization": f"Bearer {API_KEY}"}
171
  metadata = {"mimeType": "video/mp4", "displayName": Path(filepath).name}
 
203
  raise TimeoutError("File processing timed out")
204
  time.sleep(2)
205
 
206
+ # Use SDK generate when available (rest fallback also present but SDK preferred)
207
  def call_model_with_file(prompt_text: str, uploaded_file_obj):
208
  if not API_KEY:
209
  raise RuntimeError("No API key provided")
 
214
  else uploaded_file_obj.get("name") or uploaded_file_obj.get("id")
215
  )
216
 
217
+ # Prefer SDK
218
+ if HAS_GENAI and hasattr(GENAI, "responses") and hasattr(GENAI.responses, "generate"):
219
+ request = {
220
+ "model": f"models/{model_id}",
221
+ "input": [{"text": prompt_text, "files": [{"name": file_ref_name}]}],
222
+ "safetySettings": safety_settings,
223
+ "maxOutputTokens": 1000,
224
+ }
225
+ return GENAI.responses.generate(**request)
226
+
227
+ # REST v1 fallback (use short model id in URL)
228
+ model_short = model_id.split("/")[-1]
229
+ endpoint = f"https://generativeapis.googleapis.com/v1/models/{model_short}:generate"
 
 
 
230
  body = {
231
+ "input": [{"text": prompt_text, "files": [{"name": file_ref_name}]}],
 
 
 
 
 
232
  "safetySettings": safety_settings,
233
  "maxOutputTokens": 1000,
234
  }
235
  headers = {"Authorization": f"Bearer {API_KEY}", "Content-Type": "application/json"}
236
+ import requests
237
  r = requests.post(endpoint, headers=headers, json=body, timeout=180)
238
  r.raise_for_status()
239
  return r.json()