Skip to content
This repository was archived by the owner on Dec 15, 2025. It is now read-only.

Commit a987f64

Browse files
author
Toasty360
committed
initial
1 parent f46251f commit a987f64

File tree

5 files changed

+762
-109
lines changed

5 files changed

+762
-109
lines changed

src/cors.js

Lines changed: 69 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
// Function to decode base64 strings
2+
function atobPolyfill(encoded) {
3+
return decodeURIComponent(escape(globalThis.atob(encoded)));
4+
}
5+
6+
async function handleCorsRequest(request) {
7+
const urlParams = new URL(request.url).searchParams;
8+
const encodedUrl = urlParams.get("url");
9+
const headersBase64 = urlParams.get("headers");
10+
11+
if (!encodedUrl) {
12+
return new Response(
13+
"Invalid URL format. Must be a valid base64-encoded URL.",
14+
{
15+
status: 400,
16+
}
17+
);
18+
}
19+
20+
// Decode the base64-encoded URL
21+
const targetUrl = atobPolyfill(encodedUrl);
22+
23+
let decodedHeaders = {};
24+
if (headersBase64) {
25+
try {
26+
const decodedString = atobPolyfill(headersBase64);
27+
decodedHeaders = JSON.parse(decodedString);
28+
} catch (error) {
29+
return new Response(
30+
"Invalid headers format. Must be valid base64-encoded.",
31+
{
32+
status: 400,
33+
}
34+
);
35+
}
36+
}
37+
38+
// Convert the plain JSON headers object to a Headers instance
39+
const headers = new Headers();
40+
for (const [key, value] of Object.entries(decodedHeaders)) {
41+
headers.append(key, value);
42+
}
43+
44+
try {
45+
// Fetch the target URL with the specified headers
46+
const response = await fetch(targetUrl, {
47+
redirect: "follow",
48+
headers: headers, // Use the Headers object here
49+
});
50+
51+
const responseBody = await response.text();
52+
53+
// Return the response to the requester with proper CORS headers
54+
return new Response(responseBody, {
55+
status: response.status,
56+
headers: {
57+
"Access-Control-Allow-Origin": "*", // Adjust based on your CORS policy
58+
"Content-Type": response.headers.get("Content-Type") || "text/plain",
59+
},
60+
});
61+
} catch (error) {
62+
console.error("Error fetching the webpage:", error.message);
63+
return new Response("An error occurred while fetching the webpage.", {
64+
status: 500,
65+
});
66+
}
67+
}
68+
69+
export default handleCorsRequest;

src/home.js

Lines changed: 240 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,240 @@
1+
export default {
2+
async home(request) {
3+
const htmlContent = `<!DOCTYPE html>
4+
<html lang="en">
5+
6+
<head>
7+
<meta charset="UTF-8">
8+
<meta name="viewport" content="width=device-width, initial-scale=1.0">
9+
<title>Valley Proxy Player</title>
10+
<style>
11+
/* Dark theme styling */
12+
body {
13+
background-color: #282c34;
14+
color: #ffffff;
15+
font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
16+
margin: 0;
17+
padding: 0;
18+
display: flex;
19+
flex-direction: column;
20+
align-items: center;
21+
}
22+
23+
h1 {
24+
margin-top: 30px;
25+
font-size: 2em;
26+
text-align: center;
27+
}
28+
29+
p,
30+
ul,
31+
code {
32+
text-align: center;
33+
margin: 10px;
34+
font-size: 1em;
35+
line-height: 1.5;
36+
}
37+
38+
ul {
39+
list-style: none;
40+
padding: 0;
41+
}
42+
43+
li {
44+
margin: 5px 0;
45+
}
46+
47+
code {
48+
display: block;
49+
background-color: #1e1e1e;
50+
padding: 10px;
51+
border-radius: 5px;
52+
overflow-x: auto;
53+
}
54+
55+
#video-container {
56+
width: 80%;
57+
max-width: 1000px;
58+
margin: 40px auto;
59+
text-align: center;
60+
background-color: #3a3f47;
61+
padding: 20px;
62+
border-radius: 10px;
63+
box-shadow: 0 4px 15px rgba(0, 0, 0, 0.5);
64+
}
65+
66+
#m3u8UrlInput,
67+
#loadVideoButton {
68+
width: 100%;
69+
max-width: 600px;
70+
margin: 10px 0;
71+
padding: 10px;
72+
border: none;
73+
border-radius: 5px;
74+
font-size: 16px;
75+
}
76+
77+
#headersInput {
78+
width: 100%;
79+
max-width: 600px;
80+
height: 150px;
81+
/* Increased height for more space */
82+
font-size: 16px;
83+
font-family: 'Courier New', Courier, monospace;
84+
/* Fixed-width font for better JSON editing */
85+
padding: 12px;
86+
/* Added more padding */
87+
margin: 10px 0;
88+
border: none;
89+
border-radius: 5px;
90+
background-color: #555;
91+
color: #ffffff;
92+
resize: vertical;
93+
/* Allow vertical resizing for even more flexibility */
94+
}
95+
96+
#m3u8UrlInput,
97+
#headersInput {
98+
background-color: #555;
99+
color: #ffffff;
100+
}
101+
102+
#loadVideoButton {
103+
background-color: #4CAF50;
104+
color: #ffffff;
105+
cursor: pointer;
106+
transition: background-color 0.3s;
107+
}
108+
109+
#loadVideoButton:hover {
110+
background-color: #45a049;
111+
}
112+
113+
#video {
114+
width: 100%;
115+
max-width: 800px;
116+
height: 450px;
117+
margin-top: 20px;
118+
border-radius: 10px;
119+
border: 1px solid #666;
120+
}
121+
122+
.log-section {
123+
width: 80%;
124+
max-width: 800px;
125+
margin: 20px auto;
126+
padding: 20px;
127+
background-color: #3a3f47;
128+
border-radius: 10px;
129+
border: 1px solid #666;
130+
box-shadow: 0 4px 15px rgba(0, 0, 0, 0.5);
131+
}
132+
133+
#logOutput {
134+
font-size: 14px;
135+
font-family: 'Courier New', Courier, monospace;
136+
color: #ffffff;
137+
white-space: pre-wrap;
138+
background-color: #282c34;
139+
padding: 10px;
140+
border-radius: 5px;
141+
overflow-y: auto;
142+
max-height: 300px;
143+
}
144+
145+
footer {
146+
text-align: center;
147+
margin: 20px 0;
148+
font-size: 0.9em;
149+
color: #aaaaaa;
150+
}
151+
</style>
152+
</head>
153+
154+
<body>
155+
<h1>Valley Proxy Player</h1>
156+
<div id="video-container">
157+
<h2>HLS Player</h2>
158+
<input type="text" id="m3u8UrlInput" placeholder="Enter M3U8 URL" />
159+
<textarea id="headersInput" placeholder="Enter JSON headers">{}</textarea>
160+
<button id="loadVideoButton">Load Video</button>
161+
<video id="video" controls></video>
162+
</div>
163+
164+
<div class="log-section">
165+
<h3>Logs:</h3>
166+
<pre id="logOutput"></pre>
167+
</div>
168+
169+
<footer>
170+
<p>&copy; 2024 Valley Proxy Player. All rights reserved.</p>
171+
</footer>
172+
173+
<script src="https://cdn.jsdelivr.net/npm/hls.js@latest"></script>
174+
<script>
175+
const video = document.getElementById('video');
176+
const logOutput = document.getElementById('logOutput');
177+
const m3u8UrlInput = document.getElementById('m3u8UrlInput');
178+
const headersInput = document.getElementById('headersInput');
179+
const loadVideoButton = document.getElementById('loadVideoButton');
180+
181+
loadVideoButton.addEventListener('click', () => {
182+
const m3u8Url = m3u8UrlInput.value;
183+
const headers = headersInput.value;
184+
185+
if (!m3u8Url || !headers) {
186+
logMessage('Please enter both M3U8 URL and headers.');
187+
return;
188+
}
189+
190+
const encodedUrl = btoa(m3u8Url);
191+
const encodedHeaders = btoa(headers);
192+
193+
JSON.parse(headers); // This will throw if headers is not valid JSON
194+
encodedHeaders = btoa(headers);
195+
196+
const proxyUrl = \`/proxy?url=\${encodedUrl}&headers=\${encodedHeaders}\`;
197+
198+
logMessage(\`Attempting to load video from: \${proxyUrl}\`);
199+
loadVideo(proxyUrl);
200+
});
201+
202+
function loadVideo(m3u8Url) {
203+
if (Hls.isSupported()) {
204+
const hls = new Hls();
205+
hls.loadSource(m3u8Url);
206+
hls.attachMedia(video);
207+
208+
hls.on(Hls.Events.MANIFEST_PARSED, function () {
209+
logMessage('Manifest parsed, video can start.');
210+
video.play();
211+
});
212+
213+
hls.on(Hls.Events.ERROR, function (event, data) {
214+
logMessage(\`Error: \${data.type}, \${data.details}\`);
215+
});
216+
217+
} else if (video.canPlayType('application/vnd.apple.mpegurl')) {
218+
video.src = m3u8Url;
219+
video.addEventListener('loadedmetadata', function () {
220+
logMessage('Video metadata loaded, video can start.');
221+
video.play();
222+
});
223+
} else {
224+
logMessage('Your browser does not support HLS.');
225+
}
226+
}
227+
228+
function logMessage(message) {
229+
logOutput.textContent += message + '\n';
230+
}
231+
</script>
232+
</body>
233+
234+
</html>`;
235+
236+
return new Response(htmlContent, {
237+
headers: { 'Content-Type': 'text/html' },
238+
});
239+
},
240+
};

0 commit comments

Comments
 (0)