"use strict";
Object.defineProperty(exports, "__esModule", {
    value: true
});
Object.defineProperty(exports, "FetchClient", {
    enumerable: true,
    get: ()=>FetchClient
});
function _nodeBuffer() {
    const data = require("node:buffer");
    _nodeBuffer = function() {
        return data;
    };
    return data;
}
function _undici() {
    const data = require("undici");
    _undici = function() {
        return data;
    };
    return data;
}
const _fetch = require("../../../utils/fetch");
const _constants = require("../utils/constants");
class FetchClient {
    /** This client should be used for long-running commands */ strategy = "instant";
    /** All records that are queued and being sent */ entries = new Set();
    constructor({ fetch =createTelemetryFetch() , url =_constants.TELEMETRY_ENDPOINT , target =_constants.TELEMETRY_TARGET  } = {}){
        this.fetch = fetch;
        this.url = url;
        this.headers = {
            accept: "application/json",
            "content-type": "application/json",
            "user-agent": `expo-cli/${"0.22.26"}`,
            authorization: "Basic " + _nodeBuffer().Buffer.from(`${target}:`).toString("base64")
        };
    }
    queue(records, controller, request) {
        const entry = mutePromise(request);
        entry.finally(()=>this.entries.delete(entry));
        entry.controller = controller;
        entry.records = records;
        this.entries.add(entry);
        return entry;
    }
    record(record) {
        const records = Array.isArray(record) ? record : [
            record
        ];
        if (!records.length) return;
        const controller = new AbortController();
        const body = JSON.stringify({
            sentAt: new Date(),
            batch: records
        });
        return this.queue(records, controller, this.fetch(this.url, {
            body,
            method: "POST",
            signal: controller.signal,
            headers: this.headers
        }));
    }
    flush() {
        return mutePromise(Promise.all(this.entries));
    }
    abort() {
        const records = [];
        this.entries.forEach((entry)=>{
            try {
                entry.controller.abort();
                records.push(...entry.records);
            } catch  {
            // Ignore abort errors
            }
        });
        return records;
    }
}
function createTelemetryFetch() {
    const agent = new (_undici()).RetryAgent(new (_undici()).Agent(), {
        maxRetries: 3,
        retryAfter: true,
        minTimeout: 500,
        maxTimeout: 2000,
        timeoutFactor: 2
    });
    return (info, init = {})=>(0, _fetch.fetch)(extractUrl(info), {
            ...init,
            dispatcher: agent
        });
}
/** Extract the URL string from either `RequestInfo` or `URL` */ function extractUrl(info) {
    if (typeof info === "string") return info;
    if ("url" in info) return info.url;
    return info.toString();
}
/** Mute a promise by removing the original return type and hide errors */ function mutePromise(promise) {
    return promise.then(()=>{}, ()=>{});
}

//# sourceMappingURL=FetchClient.js.map