File size: 4,138 Bytes
d305959
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
// Elffuss Runtime · SDK de la caché compartida de modelos.
// ─────────────────────────────────────────────────────────────────────────────
// Embebe un iframe oculto al BROKER (origen compartido de Elffuss) y le pide los
// modelos por postMessage. Como el broker vive en un subdominio de utopiaia.com
// —igual que todas las webs de Elffuss (mismo «site»)—, comparte UNA sola OPFS:
// el modelo se descarga UNA vez y se reutiliza en claw/translator/copilot/code…
// Si el broker no está disponible, el llamador cae a su OPFS local (model-store).
export const BROKER_URL = 'https://models.elffuss.utopiaia.com/';

let _iframe = null, _ready = null, _seq = 0, _url = BROKER_URL;

function ensure(brokerURL) {
  if (_iframe) return _ready;
  _url = brokerURL;
  _iframe = document.createElement('iframe');
  _iframe.src = brokerURL; _iframe.setAttribute('aria-hidden', 'true');
  _iframe.style.cssText = 'position:absolute;width:0;height:0;border:0;left:-9999px;visibility:hidden';
  _ready = new Promise((resolve, reject) => {
    const to = setTimeout(() => reject(new Error('broker timeout')), 8000);
    const h = e => { if (e.source === _iframe.contentWindow && e.data?.kind === 'elffuss-broker-ready') { clearTimeout(to); removeEventListener('message', h); resolve(); } };
    addEventListener('message', h);
    _iframe.addEventListener('error', () => { clearTimeout(to); reject(new Error('broker no cargó')); });
  });
  (document.body || document.documentElement).appendChild(_iframe);
  return _ready;
}
const origin = () => new URL(_url).origin;

// Modelo como Blob (el navegador lo respalda en disco), desde la caché compartida.
// Descarga una vez para TODO Elffuss; el resto de webs lo leen sin red.
export async function getSharedModel(url, onProgress = () => {}, brokerURL = BROKER_URL) {
  await ensure(brokerURL);
  return new Promise((resolve, reject) => {
    const id = ++_seq;
    // Timeout por INACTIVIDAD: sin CUALQUIER mensaje del broker (progreso/file/
    // error) en IDLE ms, la carga está colgada → rechazar para caer a OPFS local.
    // No es un tope total (una descarga real tarda minutos): cada mensaje del
    // broker reinicia el reloj, así que solo salta si el broker enmudece de verdad.
    const IDLE = 30000;
    let timer;
    const arm = () => { clearTimeout(timer); timer = setTimeout(() => { removeEventListener('message', h); reject(new Error('broker sin respuesta (timeout de inactividad)')); }, IDLE); };
    const done = fn => (...a) => { clearTimeout(timer); removeEventListener('message', h); fn(...a); };
    const h = e => {
      if (e.source !== _iframe.contentWindow || e.data?.id !== id) return;
      const m = e.data;
      arm();                                    // cualquier señal del broker reinicia el reloj
      if (m.kind === 'progress') onProgress(m);
      // El broker devuelve un File respaldado en disco (structured-clone por
      // referencia): no copia los GB a RAM. Se lee con .stream() al subirlo a GPU.
      else if (m.kind === 'file') done(resolve)(m.file);
      else if (m.kind === 'error') done(reject)(new Error(m.message));
    };
    addEventListener('message', h);
    arm();
    _iframe.contentWindow.postMessage({ type: 'elffuss-model-get', id, url }, origin());
  });
}

// ¿ya está en la caché compartida? (para la UI: «cargando desde caché, sin bajar»)
export async function isSharedCached(url, brokerURL = BROKER_URL) {
  try { await ensure(brokerURL); } catch { return false; }
  return new Promise(resolve => {
    const id = ++_seq; const to = setTimeout(() => { removeEventListener('message', h); resolve(false); }, 4000);
    const h = e => { if (e.source !== _iframe.contentWindow || e.data?.id !== id) return; if (e.data.kind === 'has') { clearTimeout(to); removeEventListener('message', h); resolve(!!e.data.cached); } };
    addEventListener('message', h);
    _iframe.contentWindow.postMessage({ type: 'elffuss-model-has', id, url }, origin());
  });
}