// ==UserScript== // @name Edge商店下载zip插件 // @description 从Edge扩展商店获取zip格式的插件,用于安装到chrome上 // @namespace Sency // @author Sency // @version 1.0 // @match http*://microsoftedge.microsoft.com/addons/* // @grant GM_xmlhttpRequest // @grant GM_download // @connect microsoft.com // @run-at document-idle // @nocompat Chrome // ==/UserScript== (function() { 'use strict'; //下载文件(GM_download会将后缀改回crx) function download(url, filename) { filename = filename.replace(/[\/:*?"<>|]/g, ''); //去除非法字符 return new Promise((resolve, reject) => { GM_xmlhttpRequest({ url: url, method: 'get', responseType: 'blob', overrideMimeType: 'application/zip', //不加这句脚本猫会自动安装 onload: res => { if (res.status === 200) { const href = URL.createObjectURL(res.response); const a = document.createElement('a'); a.href = href; a.download = filename; a.click(); URL.revokeObjectURL(href); resolve(); } else { reject(res.status); } }, onerror: () => reject('error') }); }); } //启用或禁用按钮 function setButtonState(button, disabled, innerText) { button.disabled = disabled; button.style.setProperty('cursor', disabled ? 'not-allowed' : 'pointer', 'important'); button.style.setProperty('opacity', disabled ? '0.3' : '1', 'important'); button.innerText = innerText; } //替换下载按钮 function replaceButton(button) { const extensionName = button.children[0].children[0].ariaLabel.slice(3); //插件名 const crxId = button.id.slice(18, 50); //插件id button.innerHTML = ''; setButtonState(button, false, '下载zip'); button.addEventListener('click', e => { e.stopImmediatePropagation(); setButtonState(button, true, '下载中'); download(`https://edge.microsoft.com/extensionwebstorebase/v1/crx?response=redirect&acceptformat=crx3&x=id%3D${crxId}%26installsource%3Dondemand%26uc`, `${extensionName}.zip`) .then(() => setButtonState(button, false, '下载zip')) .catch(err => setButtonState(button, true, '下载失败')); }, true); } //监听获取下载按钮并替换 function findAndReplaceButtons() { const buttons = document.querySelectorAll('[id^=getOrRemoveButton-]'); buttons.forEach(replaceButton); const mutationObserver = window.MutationObserver || window.WebkitMutationObserver || window.MozMutationObserver; const observer = new mutationObserver(mutations => { for (let mutation of mutations) { for (let node of mutation.addedNodes) { if (node instanceof Element) { const btns = node.id.startsWith('getOrRemoveButton-') ? [node] : node.querySelectorAll('[id^=getOrRemoveButton-]'); btns.forEach(replaceButton); } } } }); observer.observe(document, { childList: true, subtree: true }); } findAndReplaceButtons(); })();