Browse Source

测试

torsen
TorsenLi 1 year ago
parent
commit
f17dc70c34
  1. 405
      douyin/background.js
  2. 5
      douyin/manifest.json
  3. 2
      douyin/popup.html
  4. 164
      douyin/popup.js

405
douyin/background.js

@ -58,86 +58,83 @@ const windowProxyMap = new Map();
// 修改代理设置函数
function setProxyForWindow(proxyConfig, windowId, callback) {
const maxRetries = 3;
let retryCount = 0;
function trySetProxy() {
console.log(`窗口 ${windowId} 设置代理尝试 ${retryCount + 1}/${maxRetries}:`, proxyConfig);
// 存储当前窗口的代理设置
windowProxyMap.set(windowId, proxyConfig);
// 设置新的代理
const config = {
value: {
mode: "fixed_servers",
rules: {
singleProxy: {
scheme: "http",
host: proxyConfig.host,
port: parseInt(proxyConfig.port)
},
bypassList: [
"localhost",
"127.0.0.1",
"<local>"
]
}
},
scope: "regular"
console.log(`设置窗口 ${windowId} 的代理:`, {
host: proxyConfig.host,
port: proxyConfig.port,
username: proxyConfig.username
});
// 存储当前窗口的代理设置
windowProxyMap.set(windowId, proxyConfig);
// 设置认证监听器
const authHandler = function(details) {
return {
authCredentials: {
username: proxyConfig.username,
password: proxyConfig.password
}
};
};
// 移除之前的监听器(如果存在)
try {
chrome.webRequest.onAuthRequired.removeListener(authHandler);
} catch (e) {}
// 添加新的监听器
chrome.webRequest.onAuthRequired.addListener(
authHandler,
{ urls: ["<all_urls>"] },
["asyncBlocking"]
);
chrome.proxy.settings.set(
config,
function() {
if (chrome.runtime.lastError) {
console.error('设置代理失败:', chrome.runtime.lastError);
handleError(chrome.runtime.lastError);
return;
// 设置代理配置
const config = {
value: {
mode: "fixed_servers",
rules: {
singleProxy: {
scheme: "http",
host: proxyConfig.host,
port: parseInt(proxyConfig.port)
}
}
},
scope: "regular"
};
// 设置代理
chrome.proxy.settings.set(
config,
function() {
if (chrome.runtime.lastError) {
console.error('设置代理失败:', chrome.runtime.lastError);
callback(chrome.runtime.lastError);
return;
}
// 验证代理设置
chrome.proxy.settings.get(
{ incognito: false },
function(config) {
console.log(`窗口 ${windowId} 当前代理配置:`, config);
if (config.value.mode === "fixed_servers") {
// 只刷新当前窗口的标签页
chrome.tabs.query({ windowId: windowId }, function(tabs) {
let refreshedCount = 0;
if (tabs.length === 0) {
callback(null, true);
return;
}
console.log(`窗口 ${windowId} 代理设置成功`);
// 刷新标签页
chrome.tabs.query({ windowId: windowId }, function(tabs) {
if (tabs.length === 0) {
callback(null, true);
return;
}
tabs.forEach(function(tab) {
chrome.tabs.reload(tab.id, { bypassCache: true }, function() {
refreshedCount++;
if (refreshedCount === tabs.length) {
callback(null, true);
}
});
});
});
} else {
handleError(new Error('代理设置验证失败'));
let refreshedCount = 0;
tabs.forEach(function(tab) {
chrome.tabs.reload(tab.id, { bypassCache: true }, function() {
refreshedCount++;
if (refreshedCount === tabs.length) {
callback(null, true);
}
}
);
}
);
}
function handleError(error) {
if (retryCount < maxRetries - 1) {
retryCount++;
setTimeout(trySetProxy, 2000);
} else {
callback(error);
});
});
});
}
}
trySetProxy();
);
}
// 消息监听器
@ -219,7 +216,7 @@ chrome.runtime.onMessage.addListener((request, sender, sendResponse) => {
})
.catch(error => {
console.error('登录请求出错:', error);
sendResponse({ status: 'error', message: '登录请出错,请检查网络连接或稍后重试。' });
sendResponse({ status: 'error', message: '登录请出错,请检查网络连接或稍后重试。' });
});
}
@ -245,14 +242,14 @@ chrome.runtime.onMessage.addListener((request, sender, sendResponse) => {
console.error('设置代理失败:', error);
sendResponse({ success: false, error: error.message });
} else {
console.log('代理已设置到新创建无痕窗口');
console.log('代理已设置到新创建无痕窗口');
sendResponse({ success: true });
}
}
);
}, 1000);
} else {
console.error('建窗口失败');
console.error('建窗口失败');
sendResponse({ success: false, error: '创建窗口失败' });
}
});
@ -266,46 +263,84 @@ chrome.runtime.onMessage.addListener((request, sender, sendResponse) => {
const proxyList = request.proxyList;
console.log('可用代理列表:', proxyList);
if (proxyList.length < incognitoWindows.length) {
if (proxyList.length === 0) {
sendResponse({
success: false,
error: `代理数量不足,需要 ${incognitoWindows.length} 个代理,但只有 ${proxyList.length}`
error: '没有可用的代理'
});
return;
}
let completedCount = 0;
let errors = [];
let currentIndex = 0;
// 处理下一个窗口
function processNextWindow() {
if (currentIndex >= incognitoWindows.length) {
checkComplete();
return;
}
// 为每个窗口单独设置代理
incognitoWindows.forEach((window, index) => {
const proxy = proxyList[index];
const [host, port] = proxy.split(':');
const window = incognitoWindows[currentIndex];
// 检查窗口是否已经有代理设置
const existingProxy = windowProxyMap.get(window.id);
if (existingProxy) {
console.log(`窗口 ${window.id} 已有代理设置,跳过:`, {
host: existingProxy.host,
port: existingProxy.port,
username: existingProxy.username
});
completedCount++;
currentIndex++;
processNextWindow();
return;
}
if (!host || !port) {
errors.push(`代理格式错误: ${proxy}`);
// 使用循环方式获取代理配置
const proxyIndex = currentIndex % proxyList.length;
const proxy = proxyList[proxyIndex];
if (!proxy || !proxy.host || !proxy.port) {
errors.push(`代理配置无效: ${JSON.stringify(proxy)}`);
completedCount++;
checkComplete();
currentIndex++;
processNextWindow();
return;
}
// 为每个窗口设置代理时先激活该窗口
console.log(`窗口 ${window.id} 使用第 ${proxyIndex + 1} 个代理 (总共 ${proxyList.length} 个)`);
// 为窗口设置代理
chrome.windows.update(window.id, { focused: true }, () => {
setTimeout(() => {
setProxyForWindow(
{ host, port: parseInt(port) },
proxy,
window.id,
(error, success) => {
if (error) {
console.error(`窗口 ${window.id} 设置代理失败:`, error);
errors.push(`窗口 ${window.id} 设置代理失败: ${error.message}`);
} else {
console.log(`窗口 ${window.id} 使用代理:`, {
host: proxy.host,
port: proxy.port,
username: proxy.username,
password: proxy.password
});
}
completedCount++;
checkComplete();
currentIndex++;
setTimeout(processNextWindow, 1000); // 等待1秒后处理下一个窗口
}
);
}, index * 3000); // 每个窗口间隔3秒
}, 1000);
});
});
}
// 开始处理第一个窗口
processNextWindow();
function checkComplete() {
if (completedCount === incognitoWindows.length) {
@ -317,33 +352,138 @@ chrome.runtime.onMessage.addListener((request, sender, sendResponse) => {
} else {
sendResponse({
success: true,
message: `已为 ${incognitoWindows.length} 个无痕窗口设置独立代理`
message: `已为 ${incognitoWindows.length} 个无痕窗口设置代理`
});
}
}
}
} else {
sendResponse({ success: false, error: '未找到无痕窗��' });
sendResponse({ success: false, error: '未找到无痕窗' });
}
});
return true;
}
if (request.action === 'clearProxy') {
chrome.proxy.settings.clear(
{
scope: "regular"
},
() => {
if (chrome.runtime.lastError) {
console.error('清除代理失败:', chrome.runtime.lastError);
sendResponse({ success: false, error: chrome.runtime.lastError.message });
} else {
console.log('代理设置已完全清除');
sendResponse({ success: true });
try {
// 清除代理设置
chrome.proxy.settings.clear(
{ scope: "regular" },
async function() {
if (chrome.runtime.lastError) {
console.error('清除代理设置失败:', chrome.runtime.lastError);
sendResponse({ success: false, error: chrome.runtime.lastError.message });
return;
}
console.log('代理设置已清除');
try {
// 获取所有窗口
const windows = await new Promise((resolve) => {
chrome.windows.getAll({
populate: true
}, resolve);
});
// 清除代理映射
windowProxyMap.clear();
console.log('代理映射已清除');
// 清除认证缓存
const removeCache = async () => {
try {
await chrome.browsingData.remove({
"since": 0
}, {
"cache": true,
"cookies": true,
"passwords": true,
"webSQL": true,
"serviceWorkers": true,
"indexedDB": true
});
console.log('认证缓存已清除');
} catch (error) {
console.error('清除认证缓存失败:', error);
}
};
await removeCache();
// 刷新所有无痕窗口的标签页
for (const window of windows) {
if (window.incognito) {
console.log(`刷新无痕窗口 ${window.id} 的标签页`);
for (const tab of window.tabs) {
try {
// 先导航到空白页面
await new Promise((resolve) => {
chrome.tabs.update(tab.id, { url: 'about:blank' }, resolve);
});
await new Promise(resolve => setTimeout(resolve, 500));
// 然后重新加载原始URL
await new Promise((resolve) => {
chrome.tabs.reload(tab.id, { bypassCache: true }, resolve);
});
// 添加短暂延迟,避免同时刷新太多标签页
await new Promise(resolve => setTimeout(resolve, 500));
} catch (error) {
console.error(`刷新标签页 ${tab.id} 失败:`, error);
}
}
}
}
sendResponse({
success: true,
message: '已清除所有代理设置、认证缓存并刷新标签页'
});
} catch (error) {
console.error('刷新标签页时出错:', error);
sendResponse({
success: false,
error: '清除代理成功但刷新标签页失败: ' + error.message
});
}
}
);
} catch (error) {
console.error('清除代理时出错:', error);
sendResponse({ success: false, error: error.message });
}
return true;
}
if (request.action === 'getCurrentProxy') {
try {
const windowId = request.windowId;
const proxyConfig = windowProxyMap.get(windowId);
if (proxyConfig) {
sendResponse({
success: true,
proxy: {
host: proxyConfig.host,
port: proxyConfig.port,
username: proxyConfig.username
// 出于安全考虑,不返回密码
}
});
} else {
sendResponse({
success: true,
proxy: null
});
}
);
} catch (error) {
console.error('获取代理信息失败:', error);
sendResponse({
success: false,
error: error.message
});
}
return true;
}
@ -356,7 +496,7 @@ chrome.runtime.onMessage.addListener((request, sender, sendResponse) => {
});
chrome.windows.onCreated.addListener((window) => {
console.log('新窗口创:', {
console.log('新窗口创:', {
id: window.id,
incognito: window.incognito,
type: window.type,
@ -375,21 +515,23 @@ chrome.tabs.onCreated.addListener((tab) => {
});
});
// 修改错误监听器,添加更多需要忽略的误类型
// 修改错误监听器,添加更多需要忽略的误类型
chrome.webRequest.onErrorOccurred.addListener(
function(details) {
// 扩展需要忽略的错误类型列表
const ignoredErrors = [
'net::ERR_ABORTED', // 请求中断
'net::ERR_NETWORK_CHANGED', // 网络变化
'net::ERR_CONNECTION_CLOSED', // 连接关闭
'net::ERR_CACHE_MISS', // 缓存未命中
'net::ERR_EMPTY_RESPONSE', // 空响应
'net::ERR_FAILED', // 一般性失败
'net::ERR_TIMED_OUT' // 超时
'net::ERR_ABORTED', // 请求中断
'net::ERR_NETWORK_CHANGED', // 网络变化
'net::ERR_CONNECTION_CLOSED', // 连接关闭
'net::ERR_CACHE_MISS', // 缓存未命中
'net::ERR_EMPTY_RESPONSE', // 空响应
'net::ERR_FAILED', // 一般性失败
'net::ERR_TIMED_OUT', // 超时
'net::ERR_TOO_MANY_RETRIES', // 重试次数过多
'net::ERR_TUNNEL_CONNECTION_FAILED' // 隧道连接失败
];
// 略的资源类型
// 略的资源类型
const ignoredResourceTypes = [
'font', // 字体文件
'image', // 图片
@ -455,25 +597,16 @@ chrome.windows.onFocusChanged.addListener((windowId) => {
}
});
// 添加窗口焦点变化监听器
// 修改窗口焦点变化监听器
chrome.windows.onFocusChanged.addListener((windowId) => {
if (windowId !== chrome.windows.WINDOW_ID_NONE) {
const proxyConfig = windowProxyMap.get(windowId);
if (proxyConfig) {
console.log(`窗口 ${windowId} 获得焦点,恢复其代理设置:`, proxyConfig);
chrome.proxy.settings.set({
value: {
mode: "fixed_servers",
rules: {
singleProxy: {
scheme: "http",
host: proxyConfig.host,
port: parseInt(proxyConfig.port)
},
bypassList: ["localhost", "127.0.0.1", "<local>"]
}
},
scope: "regular"
setProxyForWindow(proxyConfig, windowId, (error) => {
if (error) {
console.error('恢复代理设置失败:', error);
}
});
}
}
@ -483,4 +616,18 @@ chrome.windows.onFocusChanged.addListener((windowId) => {
chrome.windows.onRemoved.addListener((windowId) => {
console.log(`窗口 ${windowId} 被关闭,移除其代理设置`);
windowProxyMap.delete(windowId);
});
});
// 添加证书错误处理
chrome.webRequest.onErrorOccurred.addListener(
function(details) {
if (details.error && details.error.includes('ERR_CERT')) {
console.log('忽略证书错误:', details.url);
return { cancel: false };
}
},
{
urls: ["<all_urls>"],
types: ["main_frame", "sub_frame", "stylesheet", "script", "image", "object", "xmlhttprequest", "other"]
}
);

5
douyin/manifest.json

@ -10,7 +10,10 @@
"cookies",
"scripting",
"proxy",
"webRequest"
"webRequest",
"webRequestAuthProvider",
"browsingData",
"webNavigation"
],
"host_permissions": [
"https://douyin.xingtongworld.com/*",

2
douyin/popup.html

@ -96,7 +96,9 @@
<button id="saveProxies">保存代理</button>
<button id="updateProxies">更新代理</button>
<button id="clearProxy">清除代理</button>
<button id="checkCurrentProxy">查看当前代理</button>
<div id="proxyStatus"></div>
<div id="currentProxyStatus"></div>
</div>
<!-- 任务管理部分 -->

164
douyin/popup.js

@ -30,7 +30,9 @@ document.addEventListener('DOMContentLoaded', function() {
updateProxiesButton: document.getElementById('updateProxies'),
proxyStatusElement: document.getElementById('proxyStatus'),
clearProxyButton: document.getElementById('clearProxy'),
checkIncognito: document.getElementById('checkIncognito')
checkIncognito: document.getElementById('checkIncognito'),
checkCurrentProxy: document.getElementById('checkCurrentProxy'),
currentProxyStatus: document.getElementById('currentProxyStatus')
};
// 检查登录状态
@ -256,7 +258,7 @@ document.addEventListener('DOMContentLoaded', function() {
populate: true // 取窗中的所有标签页
});
// 只检当前窗口中的标签页
// 只检��当前窗口中的标签页
const liveRooms = new Map(); // 存储直播间ID和第一次出现的标签页信息
const duplicates = new Map(); // 存储重复的直播间信息
@ -384,7 +386,8 @@ document.addEventListener('DOMContentLoaded', function() {
const proxyList = elements.proxyListTextarea.value
.split('\n')
.map(proxy => proxy.trim())
.filter(proxy => proxy.length > 0 && validateProxy(proxy));
.filter(proxy => proxy.length > 0 && validateProxy(proxy))
.map(proxy => parseProxy(proxy)); // 解析代理字符串
if (proxyList.length === 0) {
throw new Error('没有可用的代理');
@ -482,6 +485,48 @@ document.addEventListener('DOMContentLoaded', function() {
});
});
}
// 添加查看当前代理的功能
if (elements.checkCurrentProxy) {
elements.checkCurrentProxy.addEventListener('click', async function() {
try {
// 获取当前窗口
const currentWindow = await chrome.windows.getCurrent();
// 获取代理信息
const proxyInfo = await chrome.runtime.sendMessage({
action: 'getCurrentProxy',
windowId: currentWindow.id
});
// 显示代理信息
if (elements.currentProxyStatus) {
if (proxyInfo.success) {
if (proxyInfo.proxy) {
const proxyText = `当前窗口ID: ${currentWindow.id}\n` +
`代理服务器: ${proxyInfo.proxy.host}:${proxyInfo.proxy.port}\n` +
`用户名: ${proxyInfo.proxy.username}`;
elements.currentProxyStatus.textContent = proxyText;
} else {
elements.currentProxyStatus.textContent = '当前窗口未设置代理';
}
} else {
elements.currentProxyStatus.textContent = proxyInfo.error || '获取代理信息失败';
}
// 3秒后清除状态信息
setTimeout(() => {
elements.currentProxyStatus.textContent = '';
}, 3000);
}
} catch (error) {
console.error('查看代理信息失败:', error);
if (elements.currentProxyStatus) {
elements.currentProxyStatus.textContent = '查看代理信息失败: ' + error.message;
}
}
});
}
});
// 辅助函数:获取直播间人数
@ -596,52 +641,83 @@ function validateTask(task) {
return isValidIp && isValidPort;
}
// 添加代理验证函数
// 修改代理验证函数
function validateProxy(proxy) {
const [host, port] = proxy.split(':');
if (!host || !port) return false;
// 验证IP格式
const isValidIp = host.split('.').length === 4 &&
host.split('.').every(num => {
const n = parseInt(num);
return !isNaN(n) && n >= 0 && n <= 255;
});
// 验证端口
const isValidPort = !isNaN(parseInt(port)) &&
parseInt(port) > 0 &&
parseInt(port) <= 65535;
try {
// 移除 http:// 前缀(如果存在)
if (proxy.startsWith('http://')) {
proxy = proxy.substring(7);
}
let host, port;
if (proxy.includes('@')) {
// 带认证信息的格式
const [auth, address] = proxy.split('@');
// 验证认证信息
const [username, password] = auth.split(':');
if (!username || !password) return false;
[host, port] = address.split(':');
} else {
// 简单格式
[host, port] = proxy.split(':');
}
if (!host || !port) return false;
// 验证IP格式
const isValidIp = host.split('.').length === 4 &&
host.split('.').every(num => {
const n = parseInt(num);
return !isNaN(n) && n >= 0 && n <= 255;
});
return isValidIp && isValidPort;
// 验证端口
const isValidPort = !isNaN(parseInt(port)) &&
parseInt(port) > 0 &&
parseInt(port) <= 65535;
return isValidIp && isValidPort;
} catch (error) {
console.error('代理格式验证失败:', error);
return false;
}
}
// 修改更新代理按钮的处理逻辑中的代理设置部分
async function setProxyWithRetry(proxy, maxRetries = 3) {
for (let i = 0; i < maxRetries; i++) {
try {
const [proxyHost, proxyPort] = proxy.split(':');
const response = await chrome.runtime.sendMessage({
action: 'setWindowProxy',
proxy: {
host: proxyHost,
port: parseInt(proxyPort)
}
});
// 修改代理解析函数
function parseProxy(proxyString) {
try {
// 处理完整的代理URL格式
if (proxyString.startsWith('http://')) {
// 移除 'http://' 前缀
proxyString = proxyString.substring(7);
}
if (response.success) {
return true;
}
// 如果设置失败,等待后重试
await new Promise(resolve => setTimeout(resolve, 1000 * (i + 1)));
} catch (error) {
console.error(`代理设置重试 ${i + 1} 失败:`, error);
if (i === maxRetries - 1) {
throw error;
}
let username = "", password = "", host = "", port = "";
if (proxyString.includes('@')) {
// 带认证信息的格式 username:password@host:port
const [auth, address] = proxyString.split('@');
[username, password] = auth.split(':');
[host, port] = address.split(':');
} else {
// 简单格式 host:port
[host, port] = proxyString.split(':');
}
if (!host || !port) {
throw new Error(`代理格式错误: ${proxyString}`);
}
return {
username,
password,
host,
port: parseInt(port)
};
} catch (error) {
console.error('解析代理字符串失败:', error);
throw new Error(`代理格式错误: ${proxyString}\n正确格式: http://username:password@host:port`);
}
return false;
}

Loading…
Cancel
Save