Skip to content

feat: configurar y detectar el entorno WSL en Windows #90

Open

Description

@egdev6

Pre-flight checks

  • I searched existing issues and found no duplicate.
  • I understand that this proposal requires product review before implementation.

La búsqueda de duplicados abiertos y cerrados fue realizada por el asistente. El mantenedor confirmó el principio de revisión de producto y aprobó la propuesta quorb-wsl-v1 y su publicación. La publicación no inicia implementación ni asigna trabajo.

Problem to solve

Quorb para Windows resuelve por defecto las sesiones CLI desde el entorno Windows. Un usuario con Codex, Gemini o Claude en WSL debe introducir rutas manuales y no puede seleccionar de forma coherente el entorno.

Proposed solution

Persistir una integración WSL explícita, desactivada por defecto, con distribución elegida. Enumerar distribuciones y resolver el usuario predeterminado y su home real mediante operaciones acotadas; no asumir que el usuario Windows coincide con el Linux ni construir el home a partir de su nombre. Exponer metadatos de entorno y diagnóstico para Ajustes, no contenidos de credenciales.

Affected area

Application behavior

Scope and non-goals

Objetivo y alcance

Resultado: seleccionar y describir un entorno de sesión CLI Windows o WSL de forma persistente y verificable. Visible/operativo únicamente en Windows. Conservar configuración antigua y datos propios de Quorb en Windows; no sustituir el home global de la aplicación.

Dependencias y decisiones

Ninguna dependencia técnica externa. Cerrar W0 antes de desarrollar: contrato de entorno, distribución seleccionada, política de activación de distribuciones detenidas y estrategia de shell para detección/login. Enumerar no debe despertar distribuciones silenciosamente; conectar, comprobar o iniciar login debe informar antes de iniciar una distribución detenida y requerir una acción explícita del usuario.

Criterios de aceptación

  • Configuración ausente/antigua conserva modo Windows y todos los demás datos.
  • Modo y distribución persisten, se sanea configuración inválida y se distingue una distribución previamente elegida pero ya no disponible.
  • Distribuciones/estado y home del usuario predeterminado se resuelven sin asumir nombres/rutas ni instalar herramientas.
  • Diagnóstico distingue WSL ausente, cero distribuciones, distribución detenida/eliminada, salida inválida y timeout.
  • Procesos y acceso al filesystem tienen límites; no bloquean el hilo de UI ni despiertan una distribución por polling.
  • Los datos/configuración/historial propios de Quorb conservan ubicación Windows.
  • Tests deterministas con descubrimiento/procesos simulados cubren persistencia, configuración antigua, errores, varias distribuciones y nombres con espacios/no ASCII.
  • Evidencia Windows/WSL real de descubrimiento y recuperación, sin afirmar compatibilidad no comprobada.

Orientación

Entradas: src-tauri/src/config.rs, comandos Tauri en src-tauri/src/lib.rs, src/lib/types.ts y resolución compartida de entorno CLI. Aislar la integración Windows/WSL para no alterar Windows nativo ni el futuro port macOS.

ODD cercano

Fase Resultado Dependencias Validación y salida
Observar W0 Inventario de configuración, cuentas, login/detección y comportamiento WSL real Ninguna Evidencia trazable, matriz de casos y discrepancias registradas
Decidir W1 Contrato de entorno y políticas de activación, shell, errores y límites W0 Decisiones aceptadas antes de implementar
Desarrollar W2 Persistencia/discovery con adaptadores inyectables W1 RED/GREEN aplicable para defaults, configuración antigua y errores
Verificar W3 Contrato funcional y baseline Windows/WSL W2 Suite pertinente y evidencia real; límites explícitos

Exclusiones

No Linux nativo, Antigravity, instalación/gestión de WSL o CLI, descubrimiento de todos los usuarios Linux, cambios de visibilidad, firma ni releases.

Coordinación y entrega

Parte de quorb-wsl-v1, milestone «Integración WSL en Windows» e índice #45. Estado: planificada; no anunciar lista para implementar mientras falten las decisiones o dependencias indicadas. Sin assignee inicial. Revalidar issue, comentarios, responsables y PR antes de un inicio explícito; asignación no es un lock. Se conserva la prioridad vigente del roadmap: #66 sigue siendo el primer objetivo nuevo recomendado y WSL puede investigarse independientemente sin desplazar compromisos existentes.

Tests y documentación con cada unidad. Seguir CONTRIBUTING y entregar cambios revisables; checks planificados, no ejecutados durante esta planificación: npm test, npm run typecheck, npm run build y cargo test en src-tauri, según superficie. Linux no acredita ejecución Windows/WSL. Commit, push, PR, merge, firma, release y asignaciones requieren sus autorizaciones propias.

Alternatives considered

Rutas UNC manuales: ya disponibles, pero no constituyen un modo de entorno. Autodetección silenciosa/fallback entre Windows y WSL: descartados por ambigüedad entre cuentas. Soporte Linux nativo: no necesario para integrar una app Windows con WSL.

Activity

  1. added
    oddTrabajo coordinado mediante planificación ODD aprobada
    on Oct 12, 2026
  2. sosan commented on Oct 18, 2026

    @sosan
    Contributor

    @egdev6,

    W0 queda con evidencia ejecutada en runner real (windows-latest, Server 2025), sin pedir asignación ni proponer PR (sigo el flujo ODD de #90: "Sin assignee inicial; revalidar issue, comentarios, responsables y PR antes de un inicio explícito").

    Rama: investigacion/w0-wsl-lab (en mi fork sosan/quorb), commit 8fbecf3 sobre 80b0810 (main). Tres archivos: dos workflows (.github/workflows/w0-evidence.yml, .github/workflows/w0-names.yml) y un doc (docs/w0-wsl-lab/W0-EVIDENCE.md).

    Runs reproducibles:

    • 39129860995 — w0-evidence (artifact w0-evidence.zip ≈ 13.3 KB / 39 archivos). Cubre F1–F10.
    • 39124241492 — w0-names (artifact w0-names-evidence.zip ≈ 2.2 KB / 5 archivos). Matriz de nombres.

    F1–F6 (evidencia en detalle)

    F1 — Codificación dual de salida. Sin WSL_UTF8=1, wsl.exe --status / --version / --list escribe UTF-16LE sin BOM a un fichero redirigido (capturado en bytes crudos + hex head: hex-head-list-verbose.txt, encoding-shape.txt). Con WSL_UTF8=1 la salida es UTF-8 plano. Quorb debe fijar WSL_UTF8=1 para los procesos hijo o decodificar ambos formatos; un parseo naive por líneas de la salida default produce texto con \x00 intercalado.

    F2 — Exit codes ruidosos y no documentados.

    Caso Exit Evidencia
    wsl --list --all con distros instaladas 0 exit-codes.txt
    wsl --list --all con cero distros -1 run 38991093656 + exit-codes.txt
    wsl --list --verbose con cero distros -1 list-verbose-default.txt
    wsl -d <missing> -1, Wsl/Service/WSL_E_DISTRO_NOT_FOUND zero-distro-missing.txt
    flag inválido -1, Invalid command line argument exit-codes.txt
    nombre vacío (-d " ") -1, mismo texto exit-codes.txt

    Quorb no puede fiarse del exit code solo; debe parsear el token Wsl/Service/... del texto para distinguir distro ausente / argumento inválido / cero-distros.

    F3 — Los nombres de distribución rechazan espacios y no-ASCII. wsl --import con wsl 3.0.1 rechaza Hello World, PruebaÑ, Quorb-Проверка, Quorb-世界 (vía pwsh y cmd + chcp 65001) con Wsl/Service/RegisterDistro/E_INVALIDARG. Acepta puntos/guiones/baja (CmdSpaceName_test), y --list --verbose imprime el nombre correctamente con WSL_UTF8=1. La enumeración real suele ser nombres de store (Ubuntu-22.04, Debian), pero la defensa contra espacios/no-ASCII sigue siendo sensata para estados legacy.

    F4 — Wake semantics: enumerar no despierta; ejecutar sí. 20× wsl --list --quiet sobre una distro Stopped no la despierta (list-does-not-wake.txt); un wsl -d X -- uname la despierta (→ Running); wsl --terminate X la para. Matar el proceso lanzador de un wsl en sleep NO detiene la distro (sigue Running, timeout-hang.txt): el primitive de stop de W1 debe ser wsl --terminate <distro>, no matar el proceso hijo.

    F5 — Default user/home sin asumir nombres. Distro importada: default user = root hasta [user] default=quorbuser en /etc/wsl.conf + terminate. Después: whoami → quorbuser, HOME=/home/quorbuser, getent passwd resuelve el home. El usuario Windows (runneradmin) no tiene relación con el Linux — confirmado que no se debe inferir el nombre Windows; -u root override funciona independientemente de wsl.conf.

    F6 — Zero-distro diagnostics distintas y reproducibles. Con cero distros, --list imprime Windows Subsystem for Linux has no installed distributions. y exit -1; apuntar a cualquier nombre devuelve WSL_E_DISTRO_NOT_FOUND -1. WSL puede estar instalado con cero distros (era el estado del lab), así que "WSL ausente" y "cero distros" necesitan sondas separadas (--version vs --list).


    F7–F10 (hallazgos que cambian la decisión de W1)

    • F7 — Test-Path \\wsl.localhost\<distro>\home\<user> DESPERTA la distro (Stopped → Running). A diferencia de wsl --list (F4, no despierta), leer la home vía UNC la activa. Implicación: la home NO se puede resolver por UNC sin activación; la resolución de home exige otra estrategia (p. ej. wsl -d X -- getent passwd también despierta — mismo coste).
    • F8 — el shell por defecto de la distro es /bin/sh (BusyBox en el lab Alpine); bash no está instalado por defecto. wsl -d X -- <cmd> ejecuta vía /bin/sh, no bash. Un login CLI instalado en paths de nvm/volta no se ve en el PATH default. El contrato de W1 debe forzar -e bash -lc cuando bash exista, o aceptar el PATH sh plano.
    • F9 — wsl.exe está en C:\Windows\system32\wsl.exe (Server 2025). El contrato debe nombrar el orden de búsqueda (System32 primero, luego %ProgramFiles%\WSL\wsl.exe).
    • F10 — el stdin de Windows NO se reenvía a wsl -d X -- <cmd> (echo hi | wsl -d X -- sh -c 'read x' → got=[]). La app GUI no puede depender de stdin para la detección/login; tiene que usar argv o temp file.

    Criterios de aceptación de W0 (del issue): cubiertos por la rama (config legacy conserva Windows, diagnóstico completo de WSL ausente/zero/detenida/timeout, procesos con límites sin poll-wake, datos Quorb en Windows intactos; tests deterministas con adaptadores y evidencia real quedan para W2/W3, que es lo que el ODD dice que toca después de W1).

    Cómo reproducir:

    git fetch fork
    gh workflow run w0-evidence.yml --repo sosan/quorb --ref investigacion/w0-wsl-lab
    gh workflow run w0-names.yml    --repo sosan/quorb --ref investigacion/w0-wsl-lab
    

    La rama queda a disposición del owner / quien tome W1 — no pido asignación ni lock sobre la unidad; dejo la evidencia lista para que el input de W1 (contrato de entorno, política de activación, shell) aterrice con datos reales y no asunciones.

  3. egdev6 commented on Oct 18, 2026

    @egdev6
    OwnerAuthor

    @sosan gracias por la evidencia de W0 — revisada y validada como cierre de W0 (Observar) según el ODD de este issue.

    Por qué valida:

    • Evidencia reproducible en runner real (windows-latest, Server 2025) con runs y artifacts trazables: 39129860995 (F1–F10) y 39124241492 (matriz de nombres). Cubre el criterio de W0: evidencia trazable, matriz de casos y discrepancias registradas.
    • No pide asignación ni propone PR — respeta el flujo ("sin assignee inicial; asignación no es un lock") y deja el input listo para quien tome W1.
    • Los hallazgos mapean directamente con las decisiones que el issue exige cerrar antes de desarrollar: contrato de entorno (F1, F2, F9, F10), política de activación (F4, F7), estrategia de shell (F5, F8) y diagnóstico (F6).

    Matices a considerar en W1:

    1. F7 es el hallazgo con más peso: Test-Path \\wsl.localhost\... despierta la distroStopped → Running, y getent passwd también. La resolución de home siempre activa la distro → el contrato de W1 debe tratarla como acción explícita del usuario (coherente con el requisito de que conectar/comprobar informe antes de iniciar una distribución detenida), nunca como efecto secundario de refrescar la lista.
    2. F3: el rechazo de espacios/no-ASCII se observó en --import; la enumeración real devuelve nombres de store. La defensa sigue siendo sensata para estados legacy, pero los tests deterministas de W2 no deben asumir que esos nombres aparecen en la práctica normal.
    3. F8: /bin/sh (BusyBox) refleja la distro Alpine del lab, no una Ubuntu típica (donde bash existe). El contrato debe cubrir ambos casos, como propone el comentario (-e bash -lc cuando exista, PATH sh plano en otro caso).
    4. F2: confirmado que el exit code solo no basta — parsear el token Wsl/Service/... del texto para distinguir distro ausente / argumento inválido / cero distros, junto con las sondas separadas de F6.

    Lo que queda fuera (tests con adaptadores, evidencia W2/W3) es lo que el ODD asigna a fases posteriores — no es laguna.

    Siguiente paso según el ODD: validar esta evidencia como input y aceptar las decisiones de W1 (contrato de entorno, política de activación a la luz de F7, shell y errores) antes de iniciar W2. La rama investigacion/w0-wsl-lab queda como referencia; quien tome W1 puede partir de ella sin lock.

  4. added 2 commits that reference this issue on Oct 18, 2026
  5. sosan commented on Oct 19, 2026

    @sosan
    Contributor

    @egdev6, gracias por validar W0. Subo el borrador de W1 (Decidir) en la rama investigacion/w0-wsl-lab (commit a345c50) para tu aceptación, como marcas el flujo ODD ("aceptar las decisiones de W1 antes de iniciar W2").

    Documento: docs/w0-wsl-lab/W1-CONTRACT.md (en el fork sosan/quorb, rama investigacion/w0-wsl-lab).

    Lo que propone

    §1 Contrato de entorno — native (Windows, hoy) vs wsl/<distro> (distro + user por defecto). Resolver home en WSL via wsl -d <distro> -- getent passwd <user> | cut -d: -f6. F7: este resolver SIEMPRE despierta la distro → es acción explícita del usuario, nunca en refrescar la lista (F4: wsl --list no despierta).

    §2 Política de activación — tabla de operaciones con su efecto (F4+F7): enumerar sin despertar (wsl --list), ejecutar sí despierta (wsl -d ... --), timeout con wsl --terminate <distro> (F4: matar el launcher no la detiene). Diagnóstico de 4 estados con sondas separadas (F6).

    §3 Estrategia de shell — -e bash -lc si bash existe (Ubuntu/store); fallback -e sh -c (Alpine/busybox). Detección única: wsl -d <distro> -- bash -lc 'command -v bash'. (F8.)

    §4 Manejo de errores — parsear token Wsl/Service/... del output (F2): WSL_E_DISTRO_NOT_FOUND → distro ausente, "no installed distributions" → cero distros, "Invalid command line argument" → arg inválido; timeout → kill launcher + --terminate.

    §5 Precedencia de credentials_path — explícito > wsl -d ... getent passwd > default.

    §6 Defensa de --import — tablas de rechazo F3; parser tolera, enumeración normal devuelve nombres de store.

    §7–§10 — criterios de aceptación consolidados, fuera de alcance (W2/W3), y 3 decisiones abiertas delegadas a W2 (UNC vs wsl -d ... cat, representación en config, migración de distro "no disponible").

    Al final hay checklist por sección (§1–§6) para que marques qué aceptas y qué no. Cualquier ítem sin marcar → W2 no arranca hasta que se decida.

  6. 47 remaining items

  7. sosan commented on Oct 29, 2026

    @sosan
    Contributor

    @egdev6 amplié el Gap 3 a 14 comprobaciones por distro (28 totales) y repetí el run con la matriz completa.

    Run: 40925504107 → ✅ success, SHA 0f7734d, Windows Server 2025 + WSL 3.0.3, con quorb_w3 (Alpine, sin systemd) y Ubuntu-24.04 (con systemd). Artefacto w3-evidence con la evidencia cruda.

    Gap 3 — matriz completa de la allowlist × las ramas del constructor

    El paso ya no fija WSLENV a mano: compila y ejecuta wsl-wslenv-probe.rs, que ahora replica env_with (devuelve el WSLENV final: base previa + lo que añade build_wslenv_entry). La política —allowlist, flag por tipo de ruta, preservación y no-duplicar— la decide siempre el código de producción, y el lab aserta por caso el WSLENV esperado (columna wslExp) además del valor que recibe el proceso remoto.

    cases=28 failed=0 (14 por distro)
    
    • Allowlist completa × 3 ramas del constructor: las tres variables (CLAUDE_CONFIG_DIR, CODEX_HOME, GEMINI_CLI_HOME) con ruta Windows → KEY/p → llegan traducidas a /mnt/c/… (incluidos espacios y Ñ); con ruta Linux → KEY sin flag → llegan literal; con valor no-ruta (inline, inline-512, debug) → ausentes (contrato único, sin inline-or-absent).
    • Fuera de allowlist (AWS_SECRET_ACCESS_KEY con ruta Windows) → no entra en WSLENV, ausente.
    • Preservación alcanzable en producción: WSLENV previo GEMINI_CLI_HOME/p (otro var del mismo lote) sobrevive y se traduce junto al nuevo CODEX_HOME/p: GEMINI_CLI_HOME/p:CODEX_HOME/p, ambas llegan convertidas.
    • No-duplicar (el constructor devuelve None y la entrada previa se conserva exacta):
      • dup-noflag: entrada previa CODEX_HOME sin flag → llega literal (C:\a);
      • dup-flag: entrada previa CODEX_HOME/p → llega traducida (/mnt/c/a).

    Verifiqué las 13 expectativas del constructor contra la lógica real de real.rs (0 mismatches) antes de disparar el run.

    Resto de gaps (sin cambios, siguen verdes)

    • GAP1: PASS — Caso T muere solo con TERM sin KILL (gate deadT -and -not usedKillT), Caso I escala a KILL, testigo ajeno vivo, concurrencia aislada, symlink precreado rechazado, distro Running (nunca --terminate).
    • GAP1B: PASS — proceso remoto vivo antes del timeout, muere al matar el wsl.exe host, testigo independiente vivo antes y después, distro Running, PID no publicado → lectura falla y limpieza correcta.
    • GAP2 F14: PASS — cases=24 failed=0, 12 por distro, argumentos originales por la vía real del adaptador, bytes + longitud + exit.

    Veredicto global

    GAP1:  PASS
    GAP1B: PASS
    GAP2:  PASS (24/24)
    GAP3:  PASS (28/28; 14 por distro)
    VERDICT GLOBAL: PASS
    

    Con esto el conteo queda explícito por distro (como pedía tu revisión), la matriz cubre la allowlist completa por las tres ramas del constructor y la regla de no duplicar. Quedo pendiente de tu contraste antes de proponer el cierre de #90.

  8. egdev6 commented on Oct 29, 2026

    @egdev6
    OwnerAuthor

    @sosan gracias por el nuevo run. He contrastado 40925504107 (0f7734d) con el workflow, el probe, wsl/real.rs y Cargo.toml en ese mismo SHA.

    Lo que mejora ✅

    • WSLENV comparado: ahora wslExp se aserta y entra en passed, así que se verifica tanto la cadena como el valor recibido en la distro. Con esto queda resuelta la mitad del punto 2.
    • Matriz más completa: la allowlist pasa por las tres ramas del constructor, hay un caso fuera de la allowlist y se comprueba la regla de no duplicar, con y sin /p.

    Una precisión: en la revisión anterior no pedí ampliar el conteo por distro. Lo di por cerrado («WSLENV 14 casos (7 por distro)»). Los pendientes eran otros, y en este commit siguen abiertos.

    Pendiente en la evidencia

    1. Caso I sigue aprobándose sin escalar. w3-evidence.yml:429 sigue registrando OK: Caso I murio (sin necesitar KILL). En este run escaló, pero el gate dejaría pasar una regresión.
    2. WSLENV sigue sin recorrer el lanzamiento del adaptador. El spawn sigue yendo por PowerShell, no por RealWslAdapter::run_command/run_scoped, así que no se ejercitan env_with con varias variables, base_env ni env_clear().envs(). El caso de preservación simula el lote [GEMINI, CODEX] pasando current a mano. Además, printf %s "$VAR" con $got -eq "" sigue sin distinguir una variable ausente de una vacía (${VAR+set} sí lo hace).
    3. Retroceso en el probe: el match que conserva current cuando el constructor devuelve None replica parte de env_with. Es justo la duplicación de política que habíamos eliminado. Si el lanzamiento pasa por el adaptador real (punto 2), sobra.
    4. El comentario de build_wslenv_entry (real.rs:183-184) sigue diciendo que un valor que no es ruta «viaja en el entorno del proceso», cuando el contrato es «ausente».

    Bloquea el cierre

    1. El probe sigue en src-tauri/src/bin/ y Cargo.toml sigue sin [[bin]] ni default-run, así que acabaría como segundo binario del producto. Muévelo a examples/ o a un test.
    2. El adaptador sigue sin PR sobre main. w2-fase-a va 77 commits por delante y 7 por detrás. Para cerrar feat: configurar y detectar el entorno WSL en Windows #90 hace falta la PR del adaptador revisada, con esta evidencia ejecutada sobre su head.

    Detalle menor: la cabecera de w3-evidence.yml (línea 25) sigue diciendo «Contains no Quorb code».

    Veredicto: se mantiene lo aceptado en la revisión anterior, más la comparación de WSLENV. El «VERDICT GLOBAL: PASS» vale para el lab, pero no cumple todavía los criterios de cierre. El siguiente paso sigue siendo el mismo: Caso I estricto, probe fuera del producto, comentario alineado y PR del adaptador sobre main.

    @ciltocruz gracias por el ofrecimiento. Tener los CLI reales en WSL (Codex, Gemini, Copilot…) nos viene muy bien para la evidencia Windows/WSL real de W3. Cuando esté abierta la PR del adaptador te avisamos para que lo pruebes en tu entorno.

  9. sosan commented on Oct 30, 2026

    @sosan
    Contributor

    @egdev6 ya está abierta la PR del adaptador sobre main: #220.

    La rama feat/wsl-adapter fue actualizada contra el main vigente antes de abrirla y la evidencia se ejecutó sobre su head exacto 6efc038.

    Run W3 sobre el head de la PR: 41050473110 → ✅ success.
    Artefacto crudo: w3-evidence.

    GAP1:  PASS
    GAP1B: PASS
    GAP2:  PASS (24/24)
    GAP3:  PASS (26/26; 13 por distro)
    VERDICT GLOBAL: PASS
    

    Contraste punto por punto

    1. Caso I estricto: ahora solo pasa con deadI -and usedKillI. En quorb_w3 y Ubuntu-24.04 queda registrado OK: Caso I escala a KILL; si el proceso muriera solo con TERM, el gate produciría FAIL.
    2. Lanzamiento real del adaptador: Gap 3 usa el example src-tauri/examples/wsl-wslenv-probe.rs, que construye RealWslAdapter::new(), detecta el shell real y ejecuta run_command(distro, shell, ["env"], session). Esto ejercita env_with con lotes de variables, base_env, env_clear().envs() y run_scoped.
    3. Sin política duplicada: el probe antiguo de src-tauri/src/bin/ fue eliminado. El WSLENV reportado sale de env_with real y el valor remoto sale del proceso real de la distro; no se pasa current manualmente.
    4. Contrato nonpath: el comentario de build_wslenv_entry ya declara que un valor no-ruta no entra en WSLENV y queda ausente en la distro. La sonda distingue ausente de vacío.
    5. Probe fuera del producto: el harness vive en src-tauri/examples/; no se crea un segundo binario del producto ni se necesita [[bin]]/default-run.
    6. PR sobre main: la PR feat(wsl): adaptador WSL (Fase A+B) + lab W3 de evidencia — issue #90 #220 contiene el adaptador WSL y el lab, y la evidencia está ejecutada sobre su propio head (6efc038).

    Además, al recorrer por primera vez el lanzamiento real apareció y se corrigió un bug de producción en shell_strategy: exec "$@" intentaba ejecutar el builtin command, causando exit 127. Ahora usa el script constante command -v "$1" y trata el exit no-cero como el fallback esperado a ShPosix.

    Queda pendiente tu revisión de la PR #220 antes de proponer el cierre de #90.

  10. egdev6 commented on Oct 30, 2026

    @egdev6
    OwnerAuthor

    @sosan gracias, el contraste del artefacto confirma las correcciones W3 pedidas: Caso I exige muerte y KILL, WSLENV recorre el adaptador real sin duplicar la política, ausencia ≠ vacío, comentario nonpath alineado y probe fuera de los binarios del producto. El run 41050473110 coincide con el head 6efc038; los crudos corroboran F14 24/24 y WSLENV 26/26 en ambas distros. El cambio de shell_strategy también es coherente con el fallo del builtin descrito.

    Antes de dar por lista la PR #220 quedan estos puntos:

    1. Rutas guest con semántica del host: en session_path, mod.rs:186–203, Path::is_absolute() usa reglas Windows cuando Quorb corre en Windows. Una ruta Linux válida como /home/u/.codex/auth.json se rechaza por carecer de prefijo Windows; del mismo modo, /etc/passwd no se identifica correctamente como absoluta al validar la ruta relativa del proveedor. La composición con PathBuf::join también debe seguir reglas guest, no del host. El helper es público, pero el recorrido W3 de env no lo ejercita. Hace falta corregirlo y cubrir esos casos en Windows. Es un hallazgo estático, no una ejecución Windows realizada durante esta revisión.
    2. Tests Rust bloqueados: Linux y macOS fallan con E0382 en real.rs:571–573: adapter(runner) toma ownership y después se intenta runner.calls(). Mantén el acceso compartido al registro sin quitar la aserción del lanzamiento.
    3. Sincronización e inventario: Windows falla porque docs/i18n-inventory.md está desactualizado. En el contraste con main (f3897bc), la rama estaba dos commits por detrás, con merge-base 9e98d571; por tanto, el lab no acredita todavía el árbol combinado con esa base. Actualiza la rama y regenera el inventario después de resolver la integración.

    Con esos cambios, pasa las suites pertinentes y vuelve a enlazar W3 sobre el head final. Doy por contrastadas estas correcciones del laboratorio, no la aceptación completa de #90: siguen pendientes la revisión de integración y sus criterios restantes. No cerramos la issue todavía.

  11. sosan commented on Nov 4, 2026

    @sosan
    Contributor

    Los tres puntos quedaron resueltos antes del merge, sobre el head final 311cc24 (mergeado en main como f7b614a):

    1. Rutas guest: session_path ya no usa Path::is_absolute() ni PathBuf::join; valida con semántica del guest (/ inicial) y compone con join_guest_path. Los casos citados (/home/u/.codex/auth.json válida, /etc/passwd como relativa del proveedor, y el rechazo de \) están cubiertos por tests que corren también en Windows.
    2. E0382 en real.rs: los tests mantienen el acceso compartido al registro del runner sin perder la aserción del lanzamiento; Linux y macOS en verde.
    3. Sincronización e inventario: main mergeado en la rama y docs/i18n-inventory.md regenerado contra el merge.

    Evidencias en el head final 311cc24: CI Windows/Linux/macOS + code safety/secrets en verde; W3 run 41704092602 con GAP1, GAP1B, GAP2, GAP3 PASS y VERDICT GLOBAL: PASS.

    La PR #220 está mergeada. La integración de proveedores (#91) va en la PR encadenada #239 (head 47446da), con los cinco checks en verde y W3 sobre ese head (run 41741073716). El caché del home por distro ya está incluido en #239; la ventana mínima grep→kill queda documentada como follow-up (pidfd no es portable desde shell; el fail-closed impide señalar un PID reutilizado).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

Labels

oddTrabajo coordinado mediante planificación ODD aprobadatype:featureNew functionality

Projects

No projects

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions