Spaces:
Runtime error
Runtime error
Update index.html
Browse files- index.html +20 -61
index.html
CHANGED
|
@@ -2,7 +2,7 @@
|
|
| 2 |
<html lang="en">
|
| 3 |
<head>
|
| 4 |
<meta charset="UTF-8">
|
| 5 |
-
<meta name="viewport" content="width=1024">
|
| 6 |
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
| 7 |
<title>Nakhoda4X Pro - Portfolio Dashboard</title>
|
| 8 |
<script src="https://cdn.tailwindcss.com"></script>
|
|
@@ -25,33 +25,13 @@
|
|
| 25 |
}
|
| 26 |
</script>
|
| 27 |
<style>
|
| 28 |
-
.trading-card:hover {
|
| 29 |
-
|
| 30 |
-
|
| 31 |
-
}
|
| 32 |
-
|
| 33 |
-
|
| 34 |
-
}
|
| 35 |
-
@keyframes pulse {
|
| 36 |
-
0%, 100% { opacity: 1; }
|
| 37 |
-
50% { opacity: 0.5; }
|
| 38 |
-
}
|
| 39 |
-
.coin-animation {
|
| 40 |
-
animation: float 3s ease-in-out infinite;
|
| 41 |
-
}
|
| 42 |
-
@keyframes float {
|
| 43 |
-
0% { transform: translateY(0px); }
|
| 44 |
-
50% { transform: translateY(-10px); }
|
| 45 |
-
100% { transform: translateY(0px); }
|
| 46 |
-
}
|
| 47 |
-
.api-form {
|
| 48 |
-
max-height: 0;
|
| 49 |
-
overflow: hidden;
|
| 50 |
-
transition: max-height 0.3s ease-in-out;
|
| 51 |
-
}
|
| 52 |
-
.api-form.open {
|
| 53 |
-
max-height: 200px;
|
| 54 |
-
}
|
| 55 |
</style>
|
| 56 |
</head>
|
| 57 |
<body class="bg-gray-100 dark:bg-darkBg transition-colors duration-300">
|
|
@@ -295,7 +275,7 @@
|
|
| 295 |
// API Configuration
|
| 296 |
let API_KEY = localStorage.getItem('bingxApiKey') || '';
|
| 297 |
let API_SECRET = localStorage.getItem('bingxApiSecret') || '';
|
| 298 |
-
const
|
| 299 |
|
| 300 |
// Toggle API Form
|
| 301 |
const toggleApiFormBtn = document.getElementById('toggle-api-form');
|
|
@@ -322,55 +302,34 @@
|
|
| 322 |
}
|
| 323 |
});
|
| 324 |
|
| 325 |
-
//
|
| 326 |
-
function
|
| 327 |
-
return CryptoJS.HmacSHA256(paramsStr, apiSecret).toString(CryptoJS.enc.Hex);
|
| 328 |
-
}
|
| 329 |
-
|
| 330 |
-
// Parse Parameters
|
| 331 |
-
function parseParams(params) {
|
| 332 |
-
const sortedKeys = Object.keys(params).sort();
|
| 333 |
-
const paramPairs = sortedKeys.map(key => `${key}=${params[key]}`);
|
| 334 |
-
const paramsStr = paramPairs.join('&');
|
| 335 |
-
return paramsStr ? `${paramsStr}×tamp=${Date.now()}` : `timestamp=${Date.now()}`;
|
| 336 |
-
}
|
| 337 |
-
|
| 338 |
-
// Fetch from API
|
| 339 |
-
async function fetchFromAPI(endpoint, params = {}) {
|
| 340 |
if (!API_KEY || !API_SECRET) {
|
| 341 |
throw new Error('API Key and Secret are not set. Please enter your credentials.');
|
| 342 |
}
|
| 343 |
-
params.recvWindow = params.recvWindow || 5000;
|
| 344 |
-
const
|
| 345 |
-
const
|
| 346 |
-
const url = `${API_BASE_URL}${endpoint}?${paramsStr}&signature=${signature}`;
|
| 347 |
-
const response = await fetch(url, {
|
| 348 |
-
method: 'GET',
|
| 349 |
-
headers: {
|
| 350 |
-
'X-BX-APIKEY': API_KEY,
|
| 351 |
-
'Content-Type': 'application/json'
|
| 352 |
-
}
|
| 353 |
-
});
|
| 354 |
if (!response.ok) {
|
| 355 |
-
const
|
| 356 |
-
throw new Error(`API Error ${response.status}: ${
|
| 357 |
}
|
| 358 |
return response.json();
|
| 359 |
}
|
| 360 |
|
| 361 |
// Fetch Specific Data
|
| 362 |
async function fetchBalance() {
|
| 363 |
-
const data = await
|
| 364 |
return data.data.find(b => b.asset === 'USDT')?.walletBalance || 0;
|
| 365 |
}
|
| 366 |
|
| 367 |
async function fetchOpenPositions() {
|
| 368 |
-
const data = await
|
| 369 |
return data.data || [];
|
| 370 |
}
|
| 371 |
|
| 372 |
async function fetchTradeHistory() {
|
| 373 |
-
const data = await
|
| 374 |
return data.data || [];
|
| 375 |
}
|
| 376 |
|
|
@@ -521,7 +480,7 @@
|
|
| 521 |
document.getElementById('refresh-btn').addEventListener('click', fetchData);
|
| 522 |
document.getElementById('sync-now').addEventListener('click', fetchData);
|
| 523 |
window.addEventListener('load', fetchData);
|
| 524 |
-
setInterval(fetchData, 120000);
|
| 525 |
</script>
|
| 526 |
</body>
|
| 527 |
</html>
|
|
|
|
| 2 |
<html lang="en">
|
| 3 |
<head>
|
| 4 |
<meta charset="UTF-8">
|
| 5 |
+
<meta name="viewport" content="width=1024">
|
| 6 |
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
| 7 |
<title>Nakhoda4X Pro - Portfolio Dashboard</title>
|
| 8 |
<script src="https://cdn.tailwindcss.com"></script>
|
|
|
|
| 25 |
}
|
| 26 |
</script>
|
| 27 |
<style>
|
| 28 |
+
.trading-card:hover { transform: translateY(-5px); box-shadow: 0 10px 25px rgba(0, 0, 0, 0.2); }
|
| 29 |
+
.animate-pulse { animation: pulse 2s cubic-bezier(0.4, 0, 0.6, 1) infinite; }
|
| 30 |
+
@keyframes pulse { 0%, 100% { opacity: 1; } 50% { opacity: 0.5; } }
|
| 31 |
+
.coin-animation { animation: float 3s ease-in-out infinite; }
|
| 32 |
+
@keyframes float { 0% { transform: translateY(0px); } 50% { transform: translateY(-10px); } 100% { transform: translateY(0px); } }
|
| 33 |
+
.api-form { max-height: 0; overflow: hidden; transition: max-height 0.3s ease-in-out; }
|
| 34 |
+
.api-form.open { max-height: 200px; }
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 35 |
</style>
|
| 36 |
</head>
|
| 37 |
<body class="bg-gray-100 dark:bg-darkBg transition-colors duration-300">
|
|
|
|
| 275 |
// API Configuration
|
| 276 |
let API_KEY = localStorage.getItem('bingxApiKey') || '';
|
| 277 |
let API_SECRET = localStorage.getItem('bingxApiSecret') || '';
|
| 278 |
+
const PROXY_URL = '/api/proxy'; // Proxy endpoint
|
| 279 |
|
| 280 |
// Toggle API Form
|
| 281 |
const toggleApiFormBtn = document.getElementById('toggle-api-form');
|
|
|
|
| 302 |
}
|
| 303 |
});
|
| 304 |
|
| 305 |
+
// Fetch from Proxy
|
| 306 |
+
async function fetchFromProxy(endpoint, params = {}) {
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 307 |
if (!API_KEY || !API_SECRET) {
|
| 308 |
throw new Error('API Key and Secret are not set. Please enter your credentials.');
|
| 309 |
}
|
| 310 |
+
params.recvWindow = params.recvWindow || 5000;
|
| 311 |
+
const url = `${PROXY_URL}?endpoint=${encodeURIComponent(endpoint)}&${new URLSearchParams(params).toString()}`;
|
| 312 |
+
const response = await fetch(url);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 313 |
if (!response.ok) {
|
| 314 |
+
const error = await response.json();
|
| 315 |
+
throw new Error(`API Error ${response.status}: ${error.error || 'Unknown error'}`);
|
| 316 |
}
|
| 317 |
return response.json();
|
| 318 |
}
|
| 319 |
|
| 320 |
// Fetch Specific Data
|
| 321 |
async function fetchBalance() {
|
| 322 |
+
const data = await fetchFromProxy('/openApi/swap/v3/user/balance');
|
| 323 |
return data.data.find(b => b.asset === 'USDT')?.walletBalance || 0;
|
| 324 |
}
|
| 325 |
|
| 326 |
async function fetchOpenPositions() {
|
| 327 |
+
const data = await fetchFromProxy('/openApi/swap/v2/user/positions', { symbol: 'BTC-USDT' });
|
| 328 |
return data.data || [];
|
| 329 |
}
|
| 330 |
|
| 331 |
async function fetchTradeHistory() {
|
| 332 |
+
const data = await fetchFromProxy('/openApi/swap/v2/user/income', { limit: 100 });
|
| 333 |
return data.data || [];
|
| 334 |
}
|
| 335 |
|
|
|
|
| 480 |
document.getElementById('refresh-btn').addEventListener('click', fetchData);
|
| 481 |
document.getElementById('sync-now').addEventListener('click', fetchData);
|
| 482 |
window.addEventListener('load', fetchData);
|
| 483 |
+
setInterval(fetchData, 120000);
|
| 484 |
</script>
|
| 485 |
</body>
|
| 486 |
</html>
|