fixed 友联监测bug
This commit is contained in:
1 parent
d04f748e85
commit
39b17bc39d
5 files changed
+467
-385
No files matched your search
+72
-39
@@ -2,6 +2,8 @@ const fs = require('fs');
|
||||
const yaml = require('js-yaml');
|
||||
const axios = require('axios');
|
||||
const path = require('path');
|
||||
const https = require('https');
|
||||
const http = require('http');
|
||||
|
||||
const linksPath = path.join(__dirname, '../themes/Ying/data/links.yaml');
|
||||
const outputPath = path.join(__dirname, '../static/link_status.json');
|
||||
@@ -11,8 +13,40 @@ if (!fs.existsSync(path.dirname(outputPath))) {
|
||||
fs.mkdirSync(path.dirname(outputPath), { recursive: true });
|
||||
}
|
||||
|
||||
// Config
|
||||
const CONCURRENCY = 10;
|
||||
const TIMEOUT = 10000;
|
||||
|
||||
// Optimized Axios Instance with Keep-Alive
|
||||
const axiosInstance = axios.create({
|
||||
timeout: TIMEOUT,
|
||||
maxRedirects: 5,
|
||||
httpAgent: new http.Agent({ keepAlive: true }),
|
||||
httpsAgent: new https.Agent({ keepAlive: true }),
|
||||
headers: {
|
||||
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36'
|
||||
},
|
||||
validateStatus: (status) => status >= 200 && status < 400
|
||||
});
|
||||
|
||||
async function checkUrl(url) {
|
||||
try {
|
||||
await axiosInstance.head(url);
|
||||
return true;
|
||||
} catch (error) {
|
||||
try {
|
||||
await axiosInstance.get(url);
|
||||
return true;
|
||||
} catch (err2) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
async function checkLinks() {
|
||||
console.log('Starting link check...');
|
||||
const start = Date.now();
|
||||
|
||||
try {
|
||||
const fileContents = fs.readFileSync(linksPath, 'utf8');
|
||||
const data = yaml.load(fileContents);
|
||||
@@ -22,50 +56,49 @@ async function checkLinks() {
|
||||
return;
|
||||
}
|
||||
|
||||
const blogs = data.blogs.filter(b => b.url);
|
||||
const results = {};
|
||||
// Process in chunks to avoid too many concurrent connections
|
||||
const batchSize = 10;
|
||||
const blogs = data.blogs;
|
||||
|
||||
for (let i = 0; i < blogs.length; i += batchSize) {
|
||||
const batch = blogs.slice(i, i + batchSize);
|
||||
await Promise.all(batch.map(async (blog) => {
|
||||
if (!blog.url) return;
|
||||
try {
|
||||
const response = await axios.head(blog.url, {
|
||||
timeout: 10000,
|
||||
maxRedirects: 5,
|
||||
headers: {
|
||||
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36'
|
||||
},
|
||||
validateStatus: (status) => status >= 200 && status < 400
|
||||
});
|
||||
results[blog.url] = true;
|
||||
console.log(`[OK] ${blog.name}`);
|
||||
} catch (error) {
|
||||
// Retry with GET if HEAD fails (some servers block HEAD)
|
||||
try {
|
||||
console.log(`[RETRY] ${blog.name} (HEAD failed, trying GET)...`);
|
||||
await axios.get(blog.url, {
|
||||
timeout: 10000,
|
||||
maxRedirects: 5,
|
||||
headers: {
|
||||
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36'
|
||||
},
|
||||
validateStatus: (status) => status >= 200 && status < 400
|
||||
});
|
||||
results[blog.url] = true;
|
||||
console.log(`[OK] ${blog.name} (GET success)`);
|
||||
} catch (err2) {
|
||||
results[blog.url] = false;
|
||||
console.log(`[FAIL] ${blog.name} - ${error.message}`);
|
||||
}
|
||||
const failedLinks = [];
|
||||
let completed = 0;
|
||||
const total = blogs.length;
|
||||
|
||||
// Concurrency Pool
|
||||
async function worker() {
|
||||
while (blogs.length > 0) {
|
||||
const blog = blogs.shift();
|
||||
const status = await checkUrl(blog.url);
|
||||
results[blog.url] = status;
|
||||
|
||||
completed++;
|
||||
const icon = status ? '🟢' : '🔴';
|
||||
console.log(`[${completed}/${total}] ${icon} ${blog.name}`);
|
||||
|
||||
if (!status) {
|
||||
failedLinks.push(`- ${blog.name}: ${blog.url}`);
|
||||
}
|
||||
}));
|
||||
}
|
||||
}
|
||||
|
||||
// Start workers
|
||||
const workers = Array(Math.min(blogs.length, CONCURRENCY))
|
||||
.fill(null)
|
||||
.map(() => worker());
|
||||
|
||||
await Promise.all(workers);
|
||||
|
||||
fs.writeFileSync(outputPath, JSON.stringify(results, null, 2));
|
||||
console.log(`Link status saved to ${outputPath}`);
|
||||
const duration = ((Date.now() - start) / 1000).toFixed(2);
|
||||
console.log(`✨ Check finished in ${duration}s. Status saved to ${outputPath}`);
|
||||
|
||||
// Write failed links to summary file for email notification
|
||||
const summaryPath = path.join(__dirname, '../failed_links_summary.txt');
|
||||
if (failedLinks.length > 0) {
|
||||
const summaryContent = `\n🚫 监测到 ${failedLinks.length} 个异常友链:\n${failedLinks.join('\n')}\n`;
|
||||
fs.writeFileSync(summaryPath, summaryContent);
|
||||
console.log(`Failed links summary saved to ${summaryPath}`);
|
||||
} else {
|
||||
fs.writeFileSync(summaryPath, '\n✅ 所有友链状态正常\n');
|
||||
}
|
||||
|
||||
} catch (e) {
|
||||
console.error(e);
|
||||
|
||||
Reference in new issue
Block a user