油猴

// ==UserScript==
// @name 企搜通-深度钻取(V21.2步进指令版)
// @namespace http://qisoutong.com/
// @version 21.2
// @description 抓满10个停止。用户点继续后翻页并重置,到新页面继续等待指令。
// @match *://map.baidu.com/*
// @grant GM_xmlhttpRequest
// ==/UserScript==

(function() {
'use strict';
const CONFIG = {
taskUrl: "https://qisoutong.com/task.php",
uploadUrl: "https://qisoutong.com/api_upload.php",
apiKey: "QS-998877"
};

function showHUD(msg, color = "#0f0") {
let panel = document.getElementById('qst_hud') || document.createElement('div');
panel.id = 'qst_hud';
panel.style = "position:fixed;top:10px;left:50%;transform:translateX(-50%);z-index:999999;background:rgba(0,0,0,0.95);color:#fff;padding:10px 25px;border-radius:50px;font-family:sans-serif;font-weight:bold;border:2px solid #8b5cf6;box-shadow:0 10px 30px rgba(0,0,0,0.8);";
if(!document.getElementById('qst_hud')) document.body.appendChild(panel);
panel.innerHTML = `企搜通 V21.2 | <span style="color:${color}">${msg}</span>`;
}

function main() {
// 实时获取服务器指令
GM_xmlhttpRequest({
method: "GET",
url: CONFIG.taskUrl + "?action=get_task&t=" + new Date().getTime(),
onload: (res) => {
// 如果服务器是 none (即 paused 状态),脚本处于绝对静止待命状态
if (res.responseText === "none") {
showHUD("已暂停:等待您在网站点击【继续生成】", "#ff4400");
return;
}

let task = JSON.parse(res.responseText);
let currentKW = document.querySelector('#sole-input')?.value || "";

// 1. 关键词切换逻辑
if (task.kw !== currentKW) {
showHUD(`切换任务 [${task.kw}]`, "#fbbf24");
localStorage.setItem('qst_idx', "1");
location.href = `https://map.baidu.com/?newmap=1&s=s%26wd%3D${encodeURIComponent(task.kw)}`;
return;
}

let idx = parseInt(localStorage.getItem('qst_idx') || "1");

// --- 2. 核心:翻页步进逻辑 ---
if (idx > 10) {
showHUD("正在执行翻页指令...", "#fbbf24");
let nextBtn = Array.from(document.querySelectorAll('a')).find(el => el.innerText.includes('下一页')) || document.querySelector('a[tid="nextPage"]');
if (nextBtn) {
localStorage.setItem('qst_idx', "1"); // 索引归位
sessionStorage.clear(); // 清空单页锁

// 关键:翻页的同时,立刻告诉服务器我要进入暂停,等待下一次点击
GM_xmlhttpRequest({
method: "GET",
url: `${CONFIG.taskUrl}?action=pause&kw=${encodeURIComponent(task.kw)}`,
onload: () => {
console.log("翻页完成,已通知后台进入暂停,等待下次指令");
nextBtn.click(); // 执行翻页跳转
}
});
return;
}
}

// --- 3. 抓取满10个后的暂停上报 ---
if (idx === 11) {
showHUD("本页已满,等待确认...", "#ff4400");
GM_xmlhttpRequest({
method: "GET",
url: `${CONFIG.taskUrl}?action=pause&kw=${encodeURIComponent(task.kw)}`
});
return;
}

// 执行正常抓取动作
doScrapeWork(idx, task.kw);
}
});
}

function doScrapeWork(idx, kw) {
let nameEl = document.querySelector('div.generalHead-left-header-title');
let backBtn = document.querySelector('.return-button, .header-back, .poi-detail-header__back, .ui3-action-return');

if (nameEl) {
// 在详情页
if (sessionStorage.getItem('qst_lock') === idx.toString()) {
if(backBtn) backBtn.click(); else window.history.back();
return;
}
showHUD(`抓取第 ${idx} 个...`, "#10b981");

let name = nameEl.innerText.trim();
let tel = document.querySelector('span.clampword.generalInfo-telnum-text')?.innerText || "";
let addr = document.querySelector('span.generalInfo-address-text')?.innerText || "";
let matches = tel.match(/(1[3-9]\d{10}|0\d{2,3}-?\d{7,8})/g);
let finalTel = matches ? [...new Set(matches)].join('/') : tel;

GM_xmlhttpRequest({
method: "POST",
url: CONFIG.uploadUrl,
data: `key=${CONFIG.apiKey}&company=${encodeURIComponent(name)}&phone=${encodeURIComponent(finalTel)}&full_address=${encodeURIComponent(addr)}&source=实时V21.2&kw=${encodeURIComponent(kw)}`,
headers: { "Content-Type": "application/x-www-form-urlencoded" }
});

// 更新进度并返回
localStorage.setItem('qst_idx', (idx + 1).toString());
sessionStorage.setItem('qst_lock', idx.toString());
setTimeout(() => { if (backBtn) backBtn.click(); else window.history.back(); }, 1500);
} else {
// 在列表页:点击对应序号的商家
let target = document.querySelector(`a.no-${idx}`);
if (target) {
target.scrollIntoView();
target.click();
} else {
showHUD(`寻找目标 no-${idx}...`);
}
}
}

// 提高心跳频率为 3 秒,让指令更即时
setInterval(main, 3000);
})();

返回首页