feat: Add server management functionality with new API endpoints and update UI to include server statistics
Publish Fast Tabler Docker image / build-and-push-fast (push) Successful in 14m34s
Publish Fast Tabler Docker image / build-and-push-fast (push) Successful in 14m34s
This commit is contained in:
+74
-3
@@ -126,16 +126,87 @@ app.post('/api/asns', async (req, res) => {
|
||||
}
|
||||
});
|
||||
|
||||
// --- Servers Routes (JSON format) ---
|
||||
|
||||
// Get servers from S3
|
||||
app.get('/api/servers', async (req, res) => {
|
||||
const params = {
|
||||
Bucket: BUCKET_NAME,
|
||||
Key: 'servers.json',
|
||||
};
|
||||
|
||||
try {
|
||||
const data = await s3.getObject(params).promise();
|
||||
const fileContent = data.Body.toString('utf-8');
|
||||
let servers = [];
|
||||
|
||||
try {
|
||||
servers = JSON.parse(fileContent);
|
||||
// Ensure it's an array
|
||||
if (!Array.isArray(servers)) {
|
||||
servers = [];
|
||||
}
|
||||
} catch (parseError) {
|
||||
console.error('Error parsing servers.json:', parseError);
|
||||
servers = [];
|
||||
}
|
||||
|
||||
res.json(servers);
|
||||
} catch (error) {
|
||||
if (error.code === 'NoSuchKey') {
|
||||
res.json([]); // Return empty array if file does not exist
|
||||
} else {
|
||||
console.error(error);
|
||||
res.status(500).send('Error reading from S3');
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
// Update servers in S3
|
||||
app.post('/api/servers', async (req, res) => {
|
||||
const { domains: servers } = req.body; // Keep name 'domains' for consistency
|
||||
|
||||
// Validate servers structure
|
||||
if (!Array.isArray(servers)) {
|
||||
return res.status(400).send('Servers must be an array');
|
||||
}
|
||||
|
||||
// Validate each server has required fields
|
||||
for (let i = 0; i < servers.length; i++) {
|
||||
const server = servers[i];
|
||||
if (!server.ip || !server.dns || !server.country || !server.provider || !server.tunnel) {
|
||||
return res.status(400).send(`Server at index ${i} is missing required fields`);
|
||||
}
|
||||
}
|
||||
|
||||
const params = {
|
||||
Bucket: BUCKET_NAME,
|
||||
Key: 'servers.json',
|
||||
Body: JSON.stringify(servers, null, 2), // Pretty print JSON
|
||||
ContentType: 'application/json',
|
||||
};
|
||||
|
||||
try {
|
||||
await s3.putObject(params).promise();
|
||||
res.send('File updated successfully');
|
||||
} catch (error) {
|
||||
console.error(error);
|
||||
res.status(500).send('Error writing to S3');
|
||||
}
|
||||
});
|
||||
|
||||
// Новый эндпоинт для получения дат последнего изменения файлов S3
|
||||
app.get('/api/s3/last-modified', async (req, res) => {
|
||||
try {
|
||||
const [domainsHead, asnsHead] = await Promise.all([
|
||||
const [domainsHead, asnsHead, serversHead] = await Promise.all([
|
||||
s3.headObject({ Bucket: BUCKET_NAME, Key: 'domains.txt' }).promise(),
|
||||
s3.headObject({ Bucket: BUCKET_NAME, Key: 'asns.txt' }).promise()
|
||||
s3.headObject({ Bucket: BUCKET_NAME, Key: 'asns.txt' }).promise(),
|
||||
s3.headObject({ Bucket: BUCKET_NAME, Key: 'servers.json' }).promise()
|
||||
]);
|
||||
res.json({
|
||||
domainsLastModified: domainsHead.LastModified ? domainsHead.LastModified.toISOString() : null,
|
||||
asnsLastModified: asnsHead.LastModified ? asnsHead.LastModified.toISOString() : null
|
||||
asnsLastModified: asnsHead.LastModified ? asnsHead.LastModified.toISOString() : null,
|
||||
serversLastModified: serversHead.LastModified ? serversHead.LastModified.toISOString() : null
|
||||
});
|
||||
} catch (error) {
|
||||
console.error(error);
|
||||
|
||||
Reference in New Issue
Block a user