tecuts commited on
Commit
eac4c7e
·
verified ·
1 Parent(s): 5863066

Delete app.py

Browse files
Files changed (1) hide show
  1. app.py +0 -187
app.py DELETED
@@ -1,187 +0,0 @@
1
- import hashlib
2
- import time
3
- import re
4
- import logging
5
- import requests
6
- import subprocess
7
- from fastapi import FastAPI, Request, HTTPException
8
- from fastapi.responses import FileResponse
9
- from fastapi.staticfiles import StaticFiles
10
- import tempfile
11
- import os
12
- import uuid
13
- import gc # Import the garbage collector module
14
- import json
15
-
16
-
17
- app = FastAPI()
18
-
19
- # Temporary directory for file storage
20
- global_download_dir = tempfile.mkdtemp()
21
- logging.basicConfig(level=logging.DEBUG)
22
-
23
- def md5(string):
24
- """Generate MD5 hash of a string."""
25
- return hashlib.md5(string.encode('utf-8')).hexdigest()
26
- # Constants
27
- BASE_URL = 'https://tecuts-request.hf.space'
28
- BASE = 'https://www.qobuz.com/api.json/0.2/'
29
- TOKEN = os.getenv('TOKEN')
30
-
31
-
32
- APP_ID = '579939560'
33
-
34
- # Custom Headers
35
- HEADERS = {
36
- 'X-App-Id': APP_ID,
37
- 'X-User-Auth-Token': TOKEN,
38
- 'User-Agent': 'Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.8.1.21) Gecko/20100312 Firefox/3.6'
39
- }
40
-
41
- @app.get('/')
42
- def main():
43
- return {"appStatus": "running"}
44
-
45
- @app.post('/track')
46
- async def fetch_data_for_url(request: Request):
47
- try:
48
- data = await request.json()
49
- except Exception as e:
50
- logging.error(f"Error parsing JSON: {e}")
51
- raise HTTPException(status_code=400, detail="Invalid JSON")
52
-
53
- url = data.get('url')
54
- if not url:
55
- raise HTTPException(status_code=400, detail="URL is required")
56
-
57
- logging.info(f'Fetching data for: {url}')
58
-
59
- track_id_match = re.search(r'\d+$', url)
60
- if not track_id_match:
61
- logging.error('Track ID not found in your input.')
62
- raise HTTPException(status_code=400, detail="Track ID not found in URL")
63
-
64
- track_id = track_id_match.group(0)
65
- timestamp = int(time.time())
66
- rSigRaw = f'trackgetFileUrlformat_id27intentstreamtrack_id{track_id}{timestamp}fa31fc13e7a28e7d70bb61e91aa9e178'
67
- rSig = md5(rSigRaw)
68
-
69
- download_url = f'{BASE}track/getFileUrl?format_id=27&intent=stream&track_id={track_id}&request_ts={timestamp}&request_sig={rSig}'
70
-
71
- response = requests.get(download_url, headers=HEADERS)
72
- if response.status_code != 200:
73
- logging.error(f"Failed to fetch the track file URL: {response.status_code}")
74
- raise HTTPException(status_code=500, detail="Failed to fetch the track file URL")
75
-
76
- file_url = response.json().get('url')
77
- if not file_url:
78
- logging.error("No file URL returned from Qobuz")
79
- raise HTTPException(status_code=500, detail="No file URL returned")
80
-
81
- # Download the FLAC file
82
- flac_file_path = os.path.join(global_download_dir, f'{uuid.uuid4()}.flac')
83
- with requests.get(file_url, stream=True) as r:
84
- r.raise_for_status()
85
- with open(flac_file_path, 'wb') as f:
86
- for chunk in r.iter_content(chunk_size=8192):
87
- f.write(chunk)
88
- logging.info(f"FLAC file downloaded at {flac_file_path}")
89
-
90
- # Convert FLAC to ALAC using a context manager to ensure proper cleanup
91
- alac_file_path = os.path.join(global_download_dir, f'{uuid.uuid4()}.m4a')
92
- with subprocess.Popen(['ffmpeg', '-i', flac_file_path, '-c:a', 'alac', alac_file_path], stdout=subprocess.PIPE, stderr=subprocess.PIPE) as process:
93
- process.communicate()
94
- logging.info(f"Converted to ALAC: {alac_file_path}")
95
-
96
- # Delete the FLAC file to free up space
97
- os.remove(flac_file_path)
98
- logging.info(f"Deleted FLAC file: {flac_file_path}")
99
-
100
- # Generate the file URL for ALAC
101
- alac_file_url = f'{BASE_URL}/file/{os.path.basename(alac_file_path)}'
102
- logging.info(f"Returning ALAC file URL: {alac_file_url}")
103
-
104
- # Force garbage collection to clear memory
105
- gc.collect()
106
-
107
- # Return the ALAC file URL to the client as JSON
108
- return {"url": alac_file_url}
109
-
110
- # Mount StaticFiles to serve files from the global download directory
111
- app.mount("/file", StaticFiles(directory=global_download_dir), name="downloads")
112
-
113
-
114
- def extract_video_id(url):
115
- # 定义正则表达式模式
116
- pattern = r'(?:(?:youtube\.com\/(?:watch\?v=|embed\/|shorts\/)|youtu\.be\/)([a-zA-Z0-9_-]{11}))'
117
-
118
- # 进行匹配
119
- match = re.search(pattern, url)
120
-
121
- if match:
122
- return match.group(1)
123
- else:
124
- return None
125
-
126
-
127
- @app.get("/yt-audio")
128
- async def yt_audio(url: str):
129
- try:
130
- # 提取视频 ID
131
- videoId = extract_video_id(url)
132
- if videoId is None:
133
- raise ValueError("Video ID extraction failed")
134
-
135
- # 设置请求头
136
- headers = {
137
- "X-Goog-Authuser": "0",
138
- "X-Origin": "https://www.youtube.com",
139
- "X-goog-Visitor-Id": "CgtMWlVXOTFCcE5Edyj9p4i9BjIKCgJVUxIEGgAgZA%3D%3D"
140
- }
141
-
142
- # 构造请求体
143
- body = {
144
- "context": {
145
- "client": {
146
- "clientName": "IOS",
147
- "clientVersion": "19.14.3",
148
- "deviceModel": "iPhone15,4"
149
- }
150
- },
151
- "videoId": videoId
152
- }
153
- Player_Url = "https://www.youtube.com/youtubei/v1/player?key=AIzaSyAO_FJ2SlqU8Q4STEHLGCilw_Y9_11qcW8&prettyPrint=false"
154
-
155
- # 发送请求
156
- logging.info(f"Sending request to URL: {url} with video ID: {videoId}")
157
- response = requests.post(
158
- Player_Url,
159
- timeout=20,
160
- json=body,
161
- headers=headers
162
- )
163
- response.raise_for_status()
164
-
165
- logging.info(f"Received response from URL: {url}, status code: {response.status_code}")
166
- return response.json()
167
-
168
- except requests.RequestException as e:
169
- logging.error(f"Request error: {str(e)}")
170
- return {"error": f"Request error: {str(e)}"}
171
- except json.JSONDecodeError as e:
172
- logging.error(f"JSON decoding error: {str(e)}")
173
- return {"error": f"JSON decoding error: {str(e)}"}
174
- except ValueError as e:
175
- logging.error(f"Value error: {str(e)}")
176
- return {"error": f"Value error: {str(e)}"}
177
- except Exception as e:
178
- logging.error(f"Unexpected error: {str(e)}")
179
- return {"error": f"Unexpected error: {str(e)}"}
180
-
181
- # Middleware to set the correct MIME type
182
- @app.middleware("http")
183
- async def set_mime_type_middleware(request: Request, call_next):
184
- response = await call_next(request)
185
- if request.url.path.endswith(".m4a"):
186
- response.headers["Content-Type"] = "audio/m4a"
187
- return response