import { Effect, Layer } from "effect";
import { Fetch, Request as FxRequest, Url } from "fx-fetch";
import { inject, onScopeDispose, provide } from "vue";
const KEY = Symbol("shwfed-table:shared-fetch-layer");
function signatureOf(request) {
  const headers = FxRequest.toHeadersRecord(request);
  const sortedHeaders = Object.keys(headers).sort().map((name) => [name, headers[name]]);
  return JSON.stringify({
    url: Url.format(FxRequest.getUrl(request)),
    method: request.method,
    headers: sortedHeaders
  });
}
export function makeCachedFetchLayer() {
  const cache = /* @__PURE__ */ new Map();
  const service = (request) => {
    if (request.method !== "GET") return Fetch.FetchLive(request);
    const key = signatureOf(request);
    const existing = cache.get(key);
    if (existing) return existing;
    let pending;
    const cached = Effect.async((resume) => {
      if (!pending) pending = Effect.runPromise(Effect.exit(Fetch.FetchLive(request)));
      pending.then((exit) => {
        resume(exit);
      });
    });
    cache.set(key, cached);
    return cached;
  };
  return Layer.succeed(Fetch.Fetch, service);
}
export function provideSharedFetchLayer() {
  const layer = makeCachedFetchLayer();
  provide(KEY, layer);
  onScopeDispose(() => {
  });
  return layer;
}
export function useSharedFetchLayer() {
  return inject(KEY, Fetch.layer);
}
