可以直接在content.js里面写一个函数获取blob数据实现自定义下载吗?
2025-09-22 01:47:16 65 分享链接 开发笔记 浏览器扩展
可以的,你可以将获取 blob 数据的逻辑单独放在 content.js
中,通过消息通信的方式与 background.js
交互。这种方式更符合模块化设计,也便于维护。
具体实现思路是:
- 在
content.js
中定义获取 blob 数据的函数,并监听来自后台的消息 background.js
检测到 blob 下载时,向content.js
发送消息请求获取 blob 数据content.js
处理请求并返回转换后的 dataURL 给后台- 后台使用新文件名重新发起下载
background.js
// 监控所有下载事件
chrome.downloads.onCreated.addListener((downloadItem) => {
console.log('检测到新下载:', downloadItem.url);
// 只处理blob类型的下载
if (!downloadItem.url.startsWith('blob:')) {
return;
}
// 1. 取消原下载
chrome.downloads.cancel(downloadItem.id, async () => {
const cancelError = chrome.runtime.lastError;
if (cancelError) {
console.error('取消下载失败:', cancelError);
return;
}
try {
// 2. 生成新文件名(可自定义规则)
const timestamp = new Date().getTime();
// 从MIME类型推测扩展名(如image/png -> png)
const ext = downloadItem.mime || 'dat';
const newFileName = `custom_${timestamp}.${ext.split('/').pop()}`;
// 3. 获取当前活跃标签页(blob所在页面)
const [tab] = await chrome.tabs.query({ active: true, currentWindow: true });
if (!tab) {
console.error('未找到活跃标签页');
return;
}
// 4. 向content.js发送消息,请求获取blob数据
chrome.tabs.sendMessage(tab.id, {
action: "fetchBlob",
blobUrl: downloadItem.url
}, (response) => {
// 处理content.js的响应
if (chrome.runtime.lastError) {
console.error('消息发送失败:', chrome.runtime.lastError);
return;
}
if (!response || !response.success) {
console.error('获取blob数据失败:', response?.error);
return;
}
// 5. 用新文件名重新下载
chrome.downloads.download({
url: response.dataUrl,
filename: newFileName,
conflictAction: 'uniquify' // 文件名冲突时自动加后缀
}, (downloadId) => {
const downloadError = chrome.runtime.lastError;
if (downloadError) {
console.error('重新下载失败:', downloadError);
} else {
console.log(`已重命名下载:${newFileName},ID:${downloadId}`);
}
});
});
} catch (error) {
console.error('处理blob下载时出错:', error);
}
});
});
content.js
// 在content script中定义获取blob数据的函数
async function getBlobData(blobUrl) {
try {
// 在网页上下文请求blob数据(此时blobUrl有效)
const response = await fetch(blobUrl);
const blob = await response.blob();
// 转换为dataURL(可跨上下文传递)
return new Promise((resolve) => {
const fileReader = new FileReader();
fileReader.onload = () => {
resolve({
dataUrl: fileReader.result,
mimeType: blob.type,
success: true
});
};
fileReader.onerror = () => {
resolve({ success: false, error: "转换blob失败" });
};
fileReader.readAsDataURL(blob);
});
} catch (error) {
console.error("content.js获取blob失败:", error);
return { success: false, error: error.message };
}
}
// 监听来自background的消息
chrome.runtime.onMessage.addListener((message, sender, sendResponse) => {
// 只处理获取blob数据的请求
if (message.action === "fetchBlob") {
// 调用获取blob的函数并返回结果
getBlobData(message.blobUrl).then(result => {
sendResponse(result);
});
// 告诉Chrome要异步发送响应
return true;
}
});
manifest.json
{
"manifest_version": 3,
"name": "Blob下载重命名工具",
"version": "1.0",
"permissions": [
"downloads",
"scripting",
"activeTab"
],
"background": {
"service_worker": "background.js"
},
"content_scripts": [
{
"matches": ["<all_urls>"], // 匹配所有网站
"js": ["content.js"], // 注入content script
"run_at": "document_idle" // 页面空闲时注入
}
]
}
代码说明
模块化分工:
content.js
:专注于在网页上下文处理 blob 数据(因为 blob URL 仅在网页上下文有效)background.js
:负责监控下载、协调流程、发起新下载- 两者通过 Chrome 的消息系统(
chrome.runtime.sendMessage
)通信
核心通信流程:
background检测到blob下载 → 取消原下载 → 向content发送获取blob请求 → content在网页上下文获取并转换blob → 返回dataURL给background → background用新文件名重新下载
优势:
- 代码分离,职责更清晰(content 处理网页相关操作,background 处理扩展核心逻辑)
- 可复用性更高(
getBlobData
函数可在其他场景调用) - 便于调试(content 脚本的日志会显示在网页的控制台,而非扩展背景页控制台)
注意事项:
content.js
仅在manifest.json
中matches
配置的网站生效,这里用<all_urls>
匹配所有网站- 消息传递是异步的,
content.js
中需要用return true
告诉 Chrome 要异步发送响应 - 如果网页有严格的 CSP(内容安全策略),可能需要在
manifest.json
中配置content_security_policy
兼容
这种方式既解决了 blob URL 跨上下文访问的问题,又保持了代码的模块化,是处理此类场景的推荐方案。
最近更新
- 2025-09-22 01:46
- 可以直接在content.js里面写一个函数获取blob数据实现自定义下载吗?
- 2025-09-22 00:17
- background.js中可通过注入脚本的方法实现获取blobUrl实现自定义下载
- 2025-09-21 17:45
- 通过MutationObserver 开发chrome浏览器扩展的实例
- 2025-09-21 17:23
- MutationObserver实例中mutation.type为childList时addedNodes节点的遍历方法。
- 2025-09-21 17:21
- MutationObserver实例中mutation.type为childList时addedNodes节点的筛选方法。
- 2025-09-21 17:09
- MutationObserver实例中mutation.type为childList时addedNodes节点具体的方法与属性。
- 2025-09-21 16:56
- MutationObserver实例中mutation.type突变类型为childList时有哪些属性、方法?
- 2025-09-21 16:46
- MutationObserver实例中mutation三种不同突变类型的属性与方法?
- 2025-09-21 16:34
- MutationObserver实例中mutation.type突变类型为attributes时有哪些属性、方法?
- 2025-09-15 18:42
- 用豆包图像生成的功能批量创作小说推文的提示词