denizaybey commited on
Commit
f5c2623
·
0 Parent(s):

Add initial implementation for Media Content Localization and Dub Quality Assessment tool

Browse files

- Introduced `app.py` with Gradio-based user interface
- Included `README.md` for documentation and instructions
- Added `requirements.txt` for dependency management

Files changed (3) hide show
  1. README.md +49 -0
  2. app.py +115 -0
  3. requirements.txt +4 -0
README.md ADDED
@@ -0,0 +1,49 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ ---
2
+ title: Localization Quality Control
3
+ emoji: 🎧
4
+ colorFrom: purple
5
+ colorTo: teal
6
+ sdk: gradio
7
+ sdk_version: 5.34.1
8
+ app_file: app.py
9
+ pinned: false
10
+ license: other
11
+ short_description: Media Content Localization and Dub Quality Assessment Space
12
+ ---
13
+
14
+ # Media Content Localization and Dub Quality Assessment Space
15
+
16
+ This Hugging Face Space provides a streamlined process for verifying and assessing the quality of dubbed media content. Users can upload original and dubbed audio files for validation and quality check.
17
+
18
+ ## Features
19
+
20
+ - Upload original and dubbed `.wav` audio files.
21
+ - Files are checked for duration constraints (maximum 30 minutes).
22
+ - Automated upload to secure storage via presigned URLs.
23
+ - Initiates an external processing pipeline for quality assessment.
24
+ - Receive status updates on processing progress.
25
+
26
+ ## Usage
27
+
28
+ 1. Upload the original and dubbed `.wav` files through the interface.
29
+ 2. Provide your email, company name, and tolerance percentage.
30
+ 3. The system will validate file durations, upload files securely, and trigger processing.
31
+ 4. Once triggered, the system will display the response indicating processing status.
32
+
33
+ ## Requirements & Setup
34
+
35
+ - Ensure your API endpoints for presigned URL retrieval and processing are correctly configured in the code.
36
+ - Install necessary packages using `pip install -r requirements.txt`.
37
+ - Run the app locally or deploy it as a Hugging Face Space.
38
+
39
+ ## Configuration
40
+
41
+ Modify the `app.py` to update your API endpoints for:
42
+ - Presigned URL generation
43
+ - Triggering the media processing pipeline
44
+
45
+ For detailed configuration options, refer to the [Hugging Face Spaces documentation](https://huggingface.co/docs/hub/spaces-config-reference).
46
+
47
+ ---
48
+
49
+ **Note:** This Space is designed solely for verification and quality assessment of media content. It does not handle sensitive user data beyond necessary communication.
app.py ADDED
@@ -0,0 +1,115 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import gradio as gr
2
+ import requests
3
+ import wave
4
+ import contextlib
5
+ import os
6
+
7
+ def process_audio(original_audio_path, dubbed_audio_path, email, company_name, tolerance):
8
+ """
9
+ This function processes the audio files, handling the logic for duration check,
10
+ file upload to presigned URLs, and triggering the processing.
11
+ """
12
+ # 1. Check the duration of both audio files.
13
+ try:
14
+ with contextlib.closing(wave.open(original_audio_path, 'r')) as f:
15
+ frames = f.getnframes()
16
+ rate = f.getframerate()
17
+ original_duration = frames / float(rate)
18
+
19
+ with contextlib.closing(wave.open(dubbed_audio_path, 'r')) as f:
20
+ frames = f.getnframes()
21
+ rate = f.getframerate()
22
+ dubbed_duration = frames / float(rate)
23
+
24
+ if original_duration > 1800 or dubbed_duration > 1800:
25
+ return "Error: Audio duration exceeds 30 minutes."
26
+
27
+ except Exception as e:
28
+ return f"Error reading audio files: {e}"
29
+
30
+ # --- ACTION REQUIRED ---
31
+ # Please replace the following placeholder URLs with your actual API endpoints.
32
+ presigned_url_endpoint = "https://your-api.com/get-presigned-urls"
33
+ processing_endpoint = "https://your-api.com/trigger-processing"
34
+ # --------------------------
35
+
36
+ # 2.1. Get presigned URLs from your endpoint.
37
+ payload = {
38
+ "files": [
39
+ {"name": os.path.basename(original_audio_path), "type": "audio/wav"},
40
+ {"name": os.path.basename(dubbed_audio_path), "type": "audio/wav"}
41
+ ]
42
+ }
43
+ try:
44
+ print(f"Requesting presigned URLs from: {presigned_url_endpoint}")
45
+ response = requests.post(presigned_url_endpoint, json=payload)
46
+ response.raise_for_status() # Raise an exception for bad status codes
47
+ presigned_data = response.json()
48
+
49
+ # IMPORTANT: Adjust the following lines based on the actual JSON response
50
+ # structure of your presigned URL endpoint.
51
+ # This example assumes a response like:
52
+ # {"original_url": "...", "dubbed_url": "..."}
53
+ original_upload_url = presigned_data['original_url']
54
+ dubbed_upload_url = presigned_data['dubbed_url']
55
+
56
+ except requests.exceptions.RequestException as e:
57
+ return f"Error getting presigned URLs: {e}"
58
+ except KeyError:
59
+ return "Error: Could not parse the presigned URL response. Please check the JSON structure."
60
+
61
+ # 2.2. Upload the audio files to the presigned URLs.
62
+ try:
63
+ print(f"Uploading original file to: {original_upload_url}")
64
+ with open(original_audio_path, 'rb') as f:
65
+ upload_response = requests.put(original_upload_url, data=f)
66
+ upload_response.raise_for_status()
67
+
68
+ print(f"Uploading dubbed file to: {dubbed_upload_url}")
69
+ with open(dubbed_audio_path, 'rb') as f:
70
+ upload_response = requests.put(dubbed_upload_url, data=f)
71
+ upload_response.raise_for_status()
72
+
73
+ except requests.exceptions.RequestException as e:
74
+ return f"Error uploading files: {e}"
75
+
76
+ # 3. Call the endpoint to trigger the processing.
77
+ processing_payload = {
78
+ "email": email,
79
+ "company_name": company_name,
80
+ "tolerance": tolerance,
81
+ # The keys here ('original_file', 'dubbed_file') should match what your
82
+ # processing API expects.
83
+ "original_file": original_upload_url,
84
+ "dubbed_file": dubbed_upload_url
85
+ }
86
+ try:
87
+ print(f"Triggering processing at: {processing_endpoint}")
88
+ processing_response = requests.post(processing_endpoint, json=processing_payload)
89
+ processing_response.raise_for_status()
90
+ # 4. Show the response as output.
91
+ return f"Processing triggered successfully. Server response: {processing_response.text}"
92
+ except requests.exceptions.RequestException as e:
93
+ return f"Error triggering processing: {e}"
94
+
95
+
96
+ # Create the Gradio interface for the application.
97
+ demo = gr.Interface(
98
+ fn=process_audio,
99
+ inputs=[
100
+ gr.Audio(type="filepath", label="Original .wav file"),
101
+ gr.Audio(type="filepath", label="Dubbed .wav file"),
102
+ gr.Textbox(label="Email"),
103
+ gr.Textbox(label="Company Name"),
104
+ gr.Slider(0, 100, value=5, label="Tolerance Percentage", info="Set the tolerance for audio comparison.")
105
+ ],
106
+ outputs=gr.Text(label="Processing Status"),
107
+ title="Audio Dubbing Verification",
108
+ description="Upload original and dubbed .wav files (under 30 minutes) to start the verification process.",
109
+ allow_flagging="never"
110
+ )
111
+
112
+ if __name__ == "__main__":
113
+ # To run this file locally, you'll need to install gradio and requests:
114
+ # pip install gradio requests
115
+ demo.launch()
requirements.txt ADDED
@@ -0,0 +1,4 @@
 
 
 
 
 
1
+ gradio
2
+ requests
3
+ wave
4
+ contextlib