VeuReu commited on
Commit
611225a
·
1 Parent(s): 30b0150

Upload 6 files

Browse files
databases.py CHANGED
@@ -251,12 +251,12 @@ def get_accessible_videos_with_sha1(session_id: str | None) -> List[Dict[str, An
251
  retorna diccionaris amb almenys les claus: video_name i sha1sum.
252
  """
253
 
254
- # 1) Vídeos públics (segons camp privacy; fallback a visibility per compatibilitat)
255
  public_rows: Dict[str, Dict[str, Any]] = {}
256
  with _connect_videos_db() as vconn:
257
  try:
258
  for row in vconn.execute(
259
- "SELECT video_name, sha1sum FROM videos WHERE COALESCE(privacy, visibility) = 'public'"
260
  ):
261
  key = row["video_name"] or row["sha1sum"]
262
  public_rows[key] = {"video_name": row["video_name"], "sha1sum": row["sha1sum"]}
 
251
  retorna diccionaris amb almenys les claus: video_name i sha1sum.
252
  """
253
 
254
+ # 1) Vídeos públics (segons camp visibility actual de la taula videos)
255
  public_rows: Dict[str, Dict[str, Any]] = {}
256
  with _connect_videos_db() as vconn:
257
  try:
258
  for row in vconn.execute(
259
+ "SELECT video_name, sha1sum FROM videos WHERE visibility = 'public'"
260
  ):
261
  key = row["video_name"] or row["sha1sum"]
262
  public_rows[key] = {"video_name": row["video_name"], "sha1sum": row["sha1sum"]}
page_modules/analyze_audiodescriptions.py CHANGED
@@ -123,6 +123,13 @@ def render_analyze_audiodescriptions_page(api, permissions: Dict[str, bool]) ->
123
  session_id = st.session_state.get("session_id")
124
  accessible_rows = get_accessible_videos_with_sha1(session_id)
125
 
 
 
 
 
 
 
 
126
  if not accessible_rows:
127
  st.info("No hi ha cap vídeo disponible per analitzar amb la sessió actual.")
128
  st.stop()
@@ -130,6 +137,16 @@ def render_analyze_audiodescriptions_page(api, permissions: Dict[str, bool]) ->
130
  # Base de media: demo/temp/media/<sha1sum>
131
  base_media_dir = Path(__file__).resolve().parent.parent / "temp" / "media"
132
 
 
 
 
 
 
 
 
 
 
 
133
  if "current_video" not in st.session_state:
134
  st.session_state.current_video = None
135
 
 
123
  session_id = st.session_state.get("session_id")
124
  accessible_rows = get_accessible_videos_with_sha1(session_id)
125
 
126
+ # DEBUG: llistar parelles <sha1sum, video_name> extretes de videos.db
127
+ try:
128
+ debug_pairs = [(row.get("sha1sum"), row.get("video_name")) for row in accessible_rows]
129
+ print(f"[DEBUG] accessible_rows (sha1sum, video_name) des de videos.db: {debug_pairs}")
130
+ except Exception as e:
131
+ print(f"[DEBUG] Error preparant debug_pairs: {e}")
132
+
133
  if not accessible_rows:
134
  st.info("No hi ha cap vídeo disponible per analitzar amb la sessió actual.")
135
  st.stop()
 
137
  # Base de media: demo/temp/media/<sha1sum>
138
  base_media_dir = Path(__file__).resolve().parent.parent / "temp" / "media"
139
 
140
+ # DEBUG: llistar subcarpetes actuals sota demo/temp/media
141
+ try:
142
+ if base_media_dir.exists():
143
+ media_subdirs = [p.name for p in sorted(base_media_dir.iterdir()) if p.is_dir()]
144
+ else:
145
+ media_subdirs = []
146
+ print(f"[DEBUG] Subcarpetes a {base_media_dir}: {media_subdirs}")
147
+ except Exception as e:
148
+ print(f"[DEBUG] Error llistant subcarpetes de media: {e}")
149
+
150
  if "current_video" not in st.session_state:
151
  st.session_state.current_video = None
152
 
page_modules/validation.py CHANGED
@@ -8,17 +8,7 @@ from typing import Dict
8
 
9
  import streamlit as st
10
 
11
-
12
- def _build_candidates(runtime_videos: Path) -> Path:
13
- candidates = [
14
- runtime_videos,
15
- Path(__file__).resolve().parent.parent / "videos",
16
- Path.cwd() / "videos",
17
- ]
18
- for candidate in candidates:
19
- if candidate.exists():
20
- return candidate
21
- return candidates[0]
22
 
23
 
24
  def render_validation_page(
@@ -35,34 +25,42 @@ def render_validation_page(
35
 
36
  tab_videos, tab_ads = st.tabs(["📹 Validar Vídeos", "🎬 Validar Audiodescripcions"])
37
 
38
- base_dir = _build_candidates(runtime_videos)
39
- if not base_dir.exists():
40
- st.info("📝 No s'ha trobat la carpeta **videos**. Crea-la i afegeix-hi subcarpetes amb els teus vídeos.")
41
- st.stop()
 
 
42
 
43
  with tab_videos:
44
  st.subheader("📹 Validar Vídeos Pujats")
45
 
46
  video_folders = []
47
- for folder in sorted(base_dir.iterdir()):
48
- if folder.is_dir() and folder.name != "completed":
49
- video_files = list(folder.glob("*.mp4")) + list(folder.glob("*.avi")) + list(folder.glob("*.mov"))
50
- if video_files:
51
- mod_time = folder.stat().st_mtime
52
- fecha = datetime.fromtimestamp(mod_time).strftime("%Y-%m-%d %H:%M")
53
- video_folders.append(
54
- {
55
- "name": folder.name,
56
- "path": str(folder),
57
- "created_at": fecha,
58
- "video_files": video_files,
59
- }
60
- )
 
 
 
 
 
 
61
 
62
  if not video_folders:
63
  st.info("📝 No hi ha vídeos pujats pendents de validació.")
64
  else:
65
- opciones_video = [f"{video['name']} - {video['created_at']}" for video in video_folders]
66
  seleccion = st.selectbox(
67
  "Selecciona un vídeo per validar:",
68
  opciones_video,
@@ -77,7 +75,7 @@ def render_validation_page(
77
 
78
  with col1:
79
  st.markdown("### 📹 Informació del Vídeo")
80
- st.markdown(f"**Nom:** {video_seleccionat['name']}")
81
  st.markdown(f"**Data:** {video_seleccionat['created_at']}")
82
  st.markdown(f"**Arxius:** {len(video_seleccionat['video_files'])} vídeos trobats")
83
 
@@ -94,9 +92,9 @@ def render_validation_page(
94
  col_btn1, col_btn2 = st.columns(2)
95
 
96
  with col_btn1:
97
- if st.button("✅ Acceptar", type="primary", key=f"accept_video_{video_seleccionat['name']}"):
98
  success = compliance_client.record_validator_decision(
99
- document_id=f"video_{video_seleccionat['name']}",
100
  validator_email=f"{username}@veureu.local",
101
  decision="acceptat",
102
  comments=f"Vídeo validat per {username}",
@@ -107,9 +105,9 @@ def render_validation_page(
107
  st.error("❌ Error registrant el veredicte")
108
 
109
  with col_btn2:
110
- if st.button("❌ Rebutjar", type="secondary", key=f"reject_video_{video_seleccionat['name']}" ):
111
  success = compliance_client.record_validator_decision(
112
- document_id=f"video_{video_seleccionat['name']}",
113
  validator_email=f"{username}@veureu.local",
114
  decision="rebutjat",
115
  comments=f"Vídeo rebutjat per {username}",
@@ -123,31 +121,35 @@ def render_validation_page(
123
  st.subheader("🎬 Validar Audiodescripcions")
124
 
125
  videos_con_ad = []
126
- if base_dir.exists():
127
- for folder in sorted(base_dir.iterdir()):
128
- if folder.is_dir() and folder.name != "completed":
129
- for subfolder_name in ["MoE", "Salamandra"]:
130
- subfolder = folder / subfolder_name
131
- if subfolder.exists():
132
- ad_files = list(subfolder.glob("*_ad.txt")) + list(subfolder.glob("*_ad.srt"))
133
- if ad_files:
134
- mod_time = folder.stat().st_mtime
135
- fecha = datetime.fromtimestamp(mod_time).strftime("%Y-%m-%d %H:%M")
136
- videos_con_ad.append(
137
- {
138
- "name": folder.name,
139
- "path": str(folder),
140
- "created_at": fecha,
141
- "ad_files": ad_files,
142
- "ad_folder": str(subfolder),
143
- }
144
- )
 
 
 
 
145
 
146
  if not videos_con_ad:
147
  st.info("📝 No hi ha audiodescripcions pendents de validació.")
148
  else:
149
  videos_ad_ordenats = sorted(videos_con_ad, key=lambda x: x["created_at"], reverse=True)
150
- opciones_ad = [f"{video['name']} - {video['created_at']}" for video in videos_ad_ordenats]
151
 
152
  seleccion_ad = st.selectbox(
153
  "Selecciona una audiodescripció per validar:",
@@ -163,7 +165,7 @@ def render_validation_page(
163
 
164
  with col1:
165
  st.markdown("### 🎬 Informació de l'Audiodescripció")
166
- st.markdown(f"**Vídeo:** {video_seleccionat['name']}")
167
  st.markdown(f"**Data:** {video_seleccionat['created_at']}")
168
  st.markdown(f"**Carpeta:** {Path(video_seleccionat['ad_folder']).name}")
169
  st.markdown(f"**Arxius:** {len(video_seleccionat['ad_files'])} audiodescripcions trobades")
@@ -185,9 +187,9 @@ def render_validation_page(
185
  col_btn1, col_btn2 = st.columns(2)
186
 
187
  with col_btn1:
188
- if st.button("✅ Acceptar", type="primary", key=f"accept_ad_{video_seleccionat['name']}"):
189
  success = compliance_client.record_validator_decision(
190
- document_id=f"ad_{video_seleccionat['name']}",
191
  validator_email=f"{username}@veureu.local",
192
  decision="acceptat",
193
  comments=f"Audiodescripció validada per {username}",
@@ -198,9 +200,9 @@ def render_validation_page(
198
  st.error("❌ Error registrant el veredicte")
199
 
200
  with col_btn2:
201
- if st.button("❌ Rebutjar", type="secondary", key=f"reject_ad_{video_seleccionat['name']}" ):
202
  success = compliance_client.record_validator_decision(
203
- document_id=f"ad_{video_seleccionat['name']}",
204
  validator_email=f"{username}@veureu.local",
205
  decision="rebutjat",
206
  comments=f"Audiodescripció rebutjada per {username}",
 
8
 
9
  import streamlit as st
10
 
11
+ from databases import get_accessible_videos_with_sha1
 
 
 
 
 
 
 
 
 
 
12
 
13
 
14
  def render_validation_page(
 
25
 
26
  tab_videos, tab_ads = st.tabs(["📹 Validar Vídeos", "🎬 Validar Audiodescripcions"])
27
 
28
+ # Llista de vídeos accessibles des de demo/temp/videos.db
29
+ session_id = st.session_state.get("session_id")
30
+ accessible_rows = get_accessible_videos_with_sha1(session_id)
31
+
32
+ # Base de media: demo/temp/media/<sha1sum>
33
+ base_media_dir = Path(__file__).resolve().parent.parent / "temp" / "media"
34
 
35
  with tab_videos:
36
  st.subheader("📹 Validar Vídeos Pujats")
37
 
38
  video_folders = []
39
+ for row in accessible_rows:
40
+ sha1 = row["sha1sum"]
41
+ video_name = row["video_name"] or row["sha1sum"]
42
+ folder = base_media_dir / sha1
43
+ if not folder.exists() or not folder.is_dir():
44
+ continue
45
+ video_files = list(folder.glob("*.mp4")) + list(folder.glob("*.avi")) + list(folder.glob("*.mov"))
46
+ if not video_files:
47
+ continue
48
+ mod_time = folder.stat().st_mtime
49
+ fecha = datetime.fromtimestamp(mod_time).strftime("%Y-%m-%d %H:%M")
50
+ video_folders.append(
51
+ {
52
+ "sha1sum": sha1,
53
+ "video_name": video_name,
54
+ "path": str(folder),
55
+ "created_at": fecha,
56
+ "video_files": video_files,
57
+ }
58
+ )
59
 
60
  if not video_folders:
61
  st.info("📝 No hi ha vídeos pujats pendents de validació.")
62
  else:
63
+ opciones_video = [f"{video['video_name']} - {video['created_at']}" for video in video_folders]
64
  seleccion = st.selectbox(
65
  "Selecciona un vídeo per validar:",
66
  opciones_video,
 
75
 
76
  with col1:
77
  st.markdown("### 📹 Informació del Vídeo")
78
+ st.markdown(f"**Nom:** {video_seleccionat['video_name']}")
79
  st.markdown(f"**Data:** {video_seleccionat['created_at']}")
80
  st.markdown(f"**Arxius:** {len(video_seleccionat['video_files'])} vídeos trobats")
81
 
 
92
  col_btn1, col_btn2 = st.columns(2)
93
 
94
  with col_btn1:
95
+ if st.button("✅ Acceptar", type="primary", key=f"accept_video_{video_seleccionat['sha1sum']}"):
96
  success = compliance_client.record_validator_decision(
97
+ document_id=f"video_{video_seleccionat['video_name']}",
98
  validator_email=f"{username}@veureu.local",
99
  decision="acceptat",
100
  comments=f"Vídeo validat per {username}",
 
105
  st.error("❌ Error registrant el veredicte")
106
 
107
  with col_btn2:
108
+ if st.button("❌ Rebutjar", type="secondary", key=f"reject_video_{video_seleccionat['video_name']}"):
109
  success = compliance_client.record_validator_decision(
110
+ document_id=f"video_{video_seleccionat['video_name']}",
111
  validator_email=f"{username}@veureu.local",
112
  decision="rebutjat",
113
  comments=f"Vídeo rebutjat per {username}",
 
121
  st.subheader("🎬 Validar Audiodescripcions")
122
 
123
  videos_con_ad = []
124
+ for row in accessible_rows:
125
+ sha1 = row["sha1sum"]
126
+ video_name = row["video_name"] or row["sha1sum"]
127
+ folder = base_media_dir / sha1
128
+ if not folder.exists() or not folder.is_dir():
129
+ continue
130
+ for subfolder_name in ["MoE", "Salamandra"]:
131
+ subfolder = folder / subfolder_name
132
+ if subfolder.exists():
133
+ ad_files = list(subfolder.glob("*_ad.txt")) + list(subfolder.glob("*_ad.srt"))
134
+ if ad_files:
135
+ mod_time = folder.stat().st_mtime
136
+ fecha = datetime.fromtimestamp(mod_time).strftime("%Y-%m-%d %H:%M")
137
+ videos_con_ad.append(
138
+ {
139
+ "sha1sum": sha1,
140
+ "video_name": video_name,
141
+ "path": str(folder),
142
+ "created_at": fecha,
143
+ "ad_files": ad_files,
144
+ "ad_folder": str(subfolder),
145
+ }
146
+ )
147
 
148
  if not videos_con_ad:
149
  st.info("📝 No hi ha audiodescripcions pendents de validació.")
150
  else:
151
  videos_ad_ordenats = sorted(videos_con_ad, key=lambda x: x["created_at"], reverse=True)
152
+ opciones_ad = [f"{video['video_name']} - {video['created_at']}" for video in videos_ad_ordenats]
153
 
154
  seleccion_ad = st.selectbox(
155
  "Selecciona una audiodescripció per validar:",
 
165
 
166
  with col1:
167
  st.markdown("### 🎬 Informació de l'Audiodescripció")
168
+ st.markdown(f"**Vídeo:** {video_seleccionat['video_name']}")
169
  st.markdown(f"**Data:** {video_seleccionat['created_at']}")
170
  st.markdown(f"**Carpeta:** {Path(video_seleccionat['ad_folder']).name}")
171
  st.markdown(f"**Arxius:** {len(video_seleccionat['ad_files'])} audiodescripcions trobades")
 
187
  col_btn1, col_btn2 = st.columns(2)
188
 
189
  with col_btn1:
190
+ if st.button("✅ Acceptar", type="primary", key=f"accept_ad_{video_seleccionat['sha1sum']}"):
191
  success = compliance_client.record_validator_decision(
192
+ document_id=f"ad_{video_seleccionat['video_name']}",
193
  validator_email=f"{username}@veureu.local",
194
  decision="acceptat",
195
  comments=f"Audiodescripció validada per {username}",
 
200
  st.error("❌ Error registrant el veredicte")
201
 
202
  with col_btn2:
203
+ if st.button("❌ Rebutjar", type="secondary", key=f"reject_ad_{video_seleccionat['sha1sum']}"):
204
  success = compliance_client.record_validator_decision(
205
+ document_id=f"ad_{video_seleccionat['video_name']}",
206
  validator_email=f"{username}@veureu.local",
207
  decision="rebutjat",
208
  comments=f"Audiodescripció rebutjada per {username}",