diff --git a/src/contentProviders/skynetProvider.ts b/src/contentProviders/skynetProvider.ts new file mode 100644 index 0000000..4cc70a3 --- /dev/null +++ b/src/contentProviders/skynetProvider.ts @@ -0,0 +1,91 @@ +import BaseProvider from "./baseProvider.js"; +import { + BlockingResponse, + HttpHeaders, + OnBeforeRequestDetailsType, + OnHeadersReceivedDetailsType, + OnRequestDetailsType, +} from "../types.js"; +import { validSkylink } from "libskynet"; +import { downloadSkylink, requestProxies } from "../util.js"; +import browser from "@lumeweb/webextension-polyfill"; + +export default class SkynetProvider extends BaseProvider { + async shouldHandleRequest( + details: OnBeforeRequestDetailsType + ): Promise { + const dns = await this.resolveDns(details); + + if (dns && validSkylink(dns)) { + return true; + } + + return false; + } + + async handleProxy(details: OnRequestDetailsType): Promise { + return requestProxies; + } + + async handleRequest( + details: OnBeforeRequestDetailsType + ): Promise { + const dns = await this.resolveDns(details); + let path = new URL(details.url).pathname; + let fileData: any, err; + try { + [fileData, err] = await downloadSkylink(dns, path); + } catch (e: any) { + debugger; + this.setData(details, "error", (e as Error).message); + return {}; + } + + if (err) { + this.setData(details, "error", err); + return {}; + } + + this.setData(details, "headers", fileData.response?.headers); + + const filter = browser.webRequest.filterResponseData(details.requestId); + + filter.ondata = () => {}; + filter.onstop = () => { + fileData.response.arrayBuffer().then((data: any) => { + filter.write(data); + filter.close(); + }); + }; + + return true; + } + + async handleHeaders( + details: OnHeadersReceivedDetailsType + ): Promise { + const err = this.getData(details, "error"); + let headers: Headers = this.getData(details, "headers") as Headers; + + if (err) { + return { + responseHeaders: [ + { + name: "Status-Code", + value: err == "404" ? "404" : "400", + }, + { + name: "Content-Type", + value: "text/html; charset=utf8", + }, + ], + }; + } + + return { + responseHeaders: Array.from(headers).map((item: string[]) => { + return { name: item[0], value: item[1] }; + }), + }; + } +}