diff --git a/src/app/service/service_worker/gm_api/gm_api.test.ts b/src/app/service/service_worker/gm_api/gm_api.test.ts index 63b937997..f05fd6793 100644 --- a/src/app/service/service_worker/gm_api/gm_api.test.ts +++ b/src/app/service/service_worker/gm_api/gm_api.test.ts @@ -315,6 +315,18 @@ describe.concurrent("native GM_download 的 @connect 校验(verifyXhrConnect expect((ret as ConfirmParam).permission).toBe("cors"); }); + it.concurrent("native 下载 data: URI 不发起网络请求,无需 @connect 也直接放行 (#1635)", async () => { + const url = `data:text/csv;charset=utf-8,${encodeURIComponent("a,b,c\n1,2,3")}`; + expect(await downloadConfirm(makeReq({ url, downloadMode: "native" }), makeConnSender(), makeGmApi())).toBe(true); + expect( + await downloadConfirm( + makeReq({ url, downloadMode: "native", connect: ["example.com"] }), + makeConnSender(), + makeGmApi() + ) + ).toBe(true); + }); + it.concurrent("native 下载:域名命中 @connect 时放行", async () => { const req = makeReq({ url: "https://api.example.com/f.zip", downloadMode: "native", connect: ["example.com"] }); const ret = await downloadConfirm(req, makeConnSender(), makeGmApi()); diff --git a/src/app/service/service_worker/gm_api/gm_api.ts b/src/app/service/service_worker/gm_api/gm_api.ts index b2c91d5d0..a658951ed 100644 --- a/src/app/service/service_worker/gm_api/gm_api.ts +++ b/src/app/service/service_worker/gm_api/gm_api.ts @@ -1398,8 +1398,10 @@ export default class GMApi { @PermissionVerify.API({ // native 下载会发起真实跨域请求,需校验黑名单 / 站点访问 / @connect。 // 与 TM 不同(TM 的 @connect 只作用于 xhr/fetch),未列入 @connect 的域名改为弹窗询问由用户决定,而非直接拒绝。 + // data: URI 内容自带、不发起网络请求,没有可校验的域名,直接放行 (#1635) confirm: async (request, sender, gmApi) => { - if (request.params[0]?.downloadMode !== "native") { + const details = request.params[0]; + if (details?.downloadMode !== "native" || /^\s*data:/i.test(details.url)) { return true; } return gmApi.verifyXhrConnect(request, sender, true);