docs(issues): 0054-0062 — deudas detectadas en sesion fn doctor
Nueve issues nuevos cubriendo deudas tecnicas descubiertas tras ejecutar fn doctor por primera vez: - 0054 deploy_server: reimplementa SSH/systemd/rsync inline en lugar de usar funciones del registry (alta). - 0055 docker_tui: usa docker CLI directo via shell en lugar de docker_* del registry (alta). - 0056 audit_uses_functions: heuristica Python no detecta `from pkg.subpkg import X` (media). - 0057 audit_uses_functions: deteccion de simbolos Go con abreviaturas falla en algunos casos (baja). - 0058 kanban uses_functions sync deferido por WIP en curso (baja). - 0059 doble tracking de apps/*/app.md (fn_registry + sub-repo) inconsistencia (media). - 0060 fn doctor secrets: subcomando para audit secrets en TODOS los repos (media). - 0061 integrar notify_telegram en deploy_server + bucle reactivo (media, depende de 0054). - 0062 politica de deprecacion para 704 funciones sin consumidores (baja, research). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,87 @@
|
||||
# 0054 — deploy_server: refactor registry-first (SSH/systemd/rsync/health/docker-compose)
|
||||
|
||||
## APP Metadata
|
||||
|
||||
| Campo | Valor |
|
||||
|-------|-------|
|
||||
| **ID** | 0054 |
|
||||
| **Estado** | pendiente |
|
||||
| **Prioridad** | alta |
|
||||
| **Tipo** | refactor — `apps/deploy_server/` |
|
||||
|
||||
## Dependencias
|
||||
|
||||
- 13 funciones del registry ya existentes y testeadas:
|
||||
- `ssh_check_go_infra`, `ssh_exec_go_infra`, `ssh_upload_go_infra`, `ssh_config_read_go_infra`, `ssh_config_find_go_infra`
|
||||
- `systemd_install_go_infra`, `systemd_restart_go_infra`, `systemd_status_go_infra`, `systemd_generate_unit_go_infra` (pure)
|
||||
- `rsync_deploy_bash_infra`, `docker_compose_remote_deploy_bash_infra`
|
||||
- `health_check_http_go_infra`
|
||||
- `vps_setup_app_go_infra`
|
||||
- Pipelines `deploy_app_remote_go_infra` y `setup_vps_app_go_infra` orquestan varias.
|
||||
|
||||
## Contexto
|
||||
|
||||
`fn doctor uses-functions` (2026-05-07) detecto que `apps/deploy_server/` no importa NADA del registry. Toda la logica SSH/systemd/rsync/health/docker-compose esta reimplementada inline en `deployer.go` (`d.sshCheck`, `d.sshExec`, `d.rsyncDeploy`, `d.healthCheck`, `d.generateUnit`, `d.installUnit`, `deployDockerCompose`).
|
||||
|
||||
Esta es la violacion mas grande de la regla `registry-first.md` actualmente activa. La app fue construida antes de que existieran las funciones del registry equivalentes; las funciones se crearon despues pero deploy_server quedo sin migrar.
|
||||
|
||||
Tras sincronizar `app.md` (2026-05-07) las 13 funciones se quitaron del frontmatter — ahora refleja la realidad pero la deuda real (registry-first compliance) sigue.
|
||||
|
||||
## Objetivo
|
||||
|
||||
Reemplazar implementaciones inline de `deployer.go` por llamadas a las funciones del registry. Resultado:
|
||||
|
||||
1. `apps/deploy_server/*.go` importa `fn-registry/functions/infra` y `fn-registry/functions/cybersecurity` segun corresponda.
|
||||
2. `app.md` declara las 13 funciones en `uses_functions`.
|
||||
3. Los tests existentes siguen pasando.
|
||||
4. `fn doctor uses-functions` reporta `deploy_server_go_infra` sin drift.
|
||||
|
||||
## Arquitectura
|
||||
|
||||
### Archivos afectados
|
||||
|
||||
- `apps/deploy_server/deployer.go` — ELIMINAR metodos `sshCheck`, `sshExec`, `sshUpload`, `rsyncDeploy`, `healthCheck`, `generateUnit`, `installUnit` y reemplazar por llamadas a funciones del registry.
|
||||
- `apps/deploy_server/docker_compose.go` — sustituir `deployDockerCompose` por `docker_compose_remote_deploy_bash_infra`.
|
||||
- `apps/deploy_server/handlers.go` (probable) — actualizar callsites.
|
||||
- `apps/deploy_server/app.md` — anadir las 13 deps en `uses_functions`.
|
||||
- `apps/deploy_server/go.mod` — anadir `replace fn-registry => ../..` si no esta.
|
||||
|
||||
## Tareas
|
||||
|
||||
### Fase 1 — preparacion
|
||||
1.1 Listar callsites actuales en deployer.go (`grep -n 'd\.\(sshCheck\|sshExec\|sshUpload\|rsyncDeploy\|healthCheck\|generateUnit\|installUnit\)\|deployDockerCompose'`).
|
||||
1.2 Verificar firmas de las funciones del registry vs los metodos inline. Documentar diferencias (parametros distintos, error wrapping).
|
||||
1.3 Anadir `replace` directive en `go.mod` si falta.
|
||||
|
||||
### Fase 2 — migracion SSH
|
||||
2.1 Reemplazar `d.sshCheck` por `infra.SshCheck`.
|
||||
2.2 Reemplazar `d.sshExec` por `infra.SshExec`.
|
||||
2.3 Reemplazar `d.sshUpload` por `infra.SshUpload`.
|
||||
2.4 Test build: `go build` en deploy_server.
|
||||
|
||||
### Fase 3 — migracion systemd
|
||||
3.1 Reemplazar `d.generateUnit` por `infra.SystemdGenerateUnit`.
|
||||
3.2 Reemplazar `d.installUnit` por `infra.SystemdInstall`.
|
||||
3.3 Reemplazar restart/status por `infra.SystemdRestart`, `infra.SystemdStatus`.
|
||||
|
||||
### Fase 4 — migracion rsync + http + docker-compose
|
||||
4.1 Reemplazar `d.rsyncDeploy` por shell-out a `bash/functions/infra/rsync_deploy.sh` (es bash, no Go).
|
||||
4.2 Reemplazar `d.healthCheck` por `infra.HealthCheckHTTP`.
|
||||
4.3 Reemplazar `deployDockerCompose` por shell-out a `bash/functions/infra/docker_compose_remote_deploy.sh`.
|
||||
|
||||
### Fase 5 — tests + docs
|
||||
5.1 Correr tests existentes. Si hay mocks de los metodos privados, actualizar.
|
||||
5.2 Actualizar `app.md` `uses_functions` con las 13 IDs (orden alfabetico).
|
||||
5.3 `fn index` y `fn doctor uses-functions` debe reportar deploy_server limpio.
|
||||
5.4 Update CHANGELOG.md con la migracion.
|
||||
|
||||
## Riesgos
|
||||
|
||||
- Las firmas inline pueden tener parametros adicionales que las del registry no exponen. Mitigacion: si la diferencia es real, abrir proposal para extender la funcion del registry, NO duplicar inline.
|
||||
- Tests con mocks de metodos privados rompen. Mitigacion: convertir a integration tests contra docker container o servidor SSH local.
|
||||
- Build cross-platform: si `infra` paquete tiene CGo y deploy_server cross-compila, validar build linux/windows.
|
||||
|
||||
## Decisiones de diseno
|
||||
|
||||
- **No crear adapter layer**. Llamada directa a las funciones del registry. Si la firma cambia entre version, se actualiza el callsite — el costo es bajo y mantiene la regla registry-first sin ceremonia.
|
||||
- Las funciones bash (`rsync_deploy`, `docker_compose_remote_deploy`) se invocan via `os/exec` con `bash <script_path>`. NO portar a Go solo para "estar en el mismo lenguaje" — la version bash funciona y es la que el registry mantiene.
|
||||
@@ -0,0 +1,87 @@
|
||||
# 0055 — docker_tui: refactor para usar funciones docker_* del registry
|
||||
|
||||
## APP Metadata
|
||||
|
||||
| Campo | Valor |
|
||||
|-------|-------|
|
||||
| **ID** | 0055 |
|
||||
| **Estado** | pendiente |
|
||||
| **Prioridad** | alta |
|
||||
| **Tipo** | refactor — `apps/docker_tui/` |
|
||||
|
||||
## Dependencias
|
||||
|
||||
- 12 funciones del registry ya existentes:
|
||||
- `docker_pull_image_go_infra`, `docker_list_containers_go_infra`, `docker_remove_container_go_infra`
|
||||
- `docker_remove_image_go_infra`, `docker_remove_network_go_infra`, `docker_create_network_go_infra`
|
||||
- `docker_stop_container_go_infra`, `docker_start_container_go_infra`, `docker_list_images_go_infra`
|
||||
- `docker_inspect_container_go_infra`, `docker_run_container_go_infra`, `docker_container_logs_go_infra`
|
||||
- Tipos relacionados en `functions/infra/` (Container, Image, Network).
|
||||
|
||||
## Contexto
|
||||
|
||||
`fn doctor uses-functions` (2026-05-07) detecto que `apps/docker_tui/` ejecuta el CLI `docker` directamente via `shell.RunWithTimeout` en `views/docker.go` (`ListContainers`, `StartContainer`, `StopContainer`...). Cero consumo del registry.
|
||||
|
||||
Como en `0054`, la TUI fue construida antes de que existieran las funciones equivalentes en `functions/infra/`. Las 12 docker_* del registry parsean output JSON de docker CLI y devuelven tipos Go — exactamente lo que la TUI necesita.
|
||||
|
||||
Tras sincronizar `app.md` (2026-05-07) las 12 funciones se quitaron — ahora refleja la realidad, pero la deuda registry-first persiste.
|
||||
|
||||
## Objetivo
|
||||
|
||||
Reemplazar `views/docker.go` (y similares) por llamadas a `functions/infra/docker_*.go`. Resultado:
|
||||
|
||||
1. `apps/docker_tui/views/docker.go` importa `fn-registry/functions/infra`.
|
||||
2. `app.md` declara las 12 docker_* funciones en `uses_functions`.
|
||||
3. TUI sigue funcionando identica (acciones lentas se mantienen lentas, no es regresion).
|
||||
4. `fn doctor uses-functions` reporta docker_tui limpio.
|
||||
|
||||
## Arquitectura
|
||||
|
||||
### Archivos afectados
|
||||
|
||||
- `apps/docker_tui/views/docker.go` — sustituir todas las llamadas inline a docker CLI por funciones del registry.
|
||||
- `apps/docker_tui/app.md` — anadir 12 deps en `uses_functions`.
|
||||
- Probable: `apps/docker_tui/handlers/` o similar segun estructura.
|
||||
|
||||
## Tareas
|
||||
|
||||
### Fase 1 — preparacion
|
||||
1.1 Listar callsites a docker CLI: `grep -rn 'shell\.Run.*docker\|exec\.Command.*"docker"' apps/docker_tui/`.
|
||||
1.2 Mapear cada accion TUI (start, stop, list, logs, inspect, ...) a la funcion del registry equivalente.
|
||||
1.3 Anadir `replace fn-registry => ../..` en `go.mod` si falta.
|
||||
|
||||
### Fase 2 — migracion list/inspect (read-only primero)
|
||||
2.1 `ListContainers` → `infra.DockerListContainers`.
|
||||
2.2 `ListImages` → `infra.DockerListImages`.
|
||||
2.3 `InspectContainer` → `infra.DockerInspectContainer`.
|
||||
2.4 Validar que tipos retornados encajan con lo que la UI espera (`Container`, `Image`).
|
||||
|
||||
### Fase 3 — migracion lifecycle (write)
|
||||
3.1 `StartContainer` → `infra.DockerStartContainer`.
|
||||
3.2 `StopContainer` → `infra.DockerStopContainer`.
|
||||
3.3 `RemoveContainer` → `infra.DockerRemoveContainer`.
|
||||
3.4 `PullImage` → `infra.DockerPullImage`.
|
||||
3.5 `RemoveImage` → `infra.DockerRemoveImage`.
|
||||
|
||||
### Fase 4 — migracion network/run/logs
|
||||
4.1 `CreateNetwork` → `infra.DockerCreateNetwork`.
|
||||
4.2 `RemoveNetwork` → `infra.DockerRemoveNetwork`.
|
||||
4.3 `RunContainer` → `infra.DockerRunContainer`.
|
||||
4.4 `ContainerLogs` → `infra.DockerContainerLogs`.
|
||||
|
||||
### Fase 5 — tests + docs
|
||||
5.1 Lanzar TUI manualmente, verificar todas las acciones funcionan (smoke test).
|
||||
5.2 Actualizar `app.md` `uses_functions`.
|
||||
5.3 `fn index` + `fn doctor uses-functions` limpio.
|
||||
5.4 Update CHANGELOG.md.
|
||||
|
||||
## Riesgos
|
||||
|
||||
- Las funciones del registry parsean output JSON; si el TUI dependia de output text-mode, las firmas cambian. Mitigacion: las funciones del registry ya exponen tipos Go estructurados, mejor ergonomia.
|
||||
- Acciones largas (PullImage, RunContainer con stream): verificar que las funciones del registry soportan streaming o callback. Si no, abrir proposal para extender.
|
||||
- Tests existentes con mocks de docker CLI rompen. Mitigacion: usar un docker daemon real para integration tests.
|
||||
|
||||
## Decisiones de diseno
|
||||
|
||||
- Como en `0054`, NO crear adapter layer. Llamadas directas.
|
||||
- Si una accion del TUI necesita algo que el registry no expone (ej. flags raros), abrir proposal `extend_existing_function` antes de duplicar.
|
||||
@@ -0,0 +1,62 @@
|
||||
# 0056 — audit_uses_functions: detectar imports Python anidados (`from pkg.subpkg import X`)
|
||||
|
||||
## APP Metadata
|
||||
|
||||
| Campo | Valor |
|
||||
|-------|-------|
|
||||
| **ID** | 0056 |
|
||||
| **Estado** | pendiente |
|
||||
| **Prioridad** | media |
|
||||
| **Tipo** | enhancement — `functions/infra/audit_uses_functions.go` |
|
||||
|
||||
## Dependencias
|
||||
|
||||
- `audit_uses_functions_go_infra` ya existe.
|
||||
- `fn doctor uses-functions` lo consume.
|
||||
|
||||
## Contexto
|
||||
|
||||
La heuristica actual de Python solo procesa `from <pkg> import <X>` donde `<pkg>` matches `python/functions/{domain}/`. NO maneja:
|
||||
|
||||
1. `from <pkg>.<subpkg> import <X>` — ej. `from metabase.cards import metabase_get_card`. Resultado: el import se ignora y `metabase_get_card_py_infra` se reporta como `unused_in_app_md`.
|
||||
2. `import <pkg>; <pkg>.<symbol>(...)` — uso indirecto.
|
||||
|
||||
Confirmado en sesion 2026-05-07: `apps/auto_metabase` y `apps/metabase_registry` tienen 8-44 falsos positivos por este motivo. Tras sincronizacion manual quedaron 4/12 apps con drift, todas por esta limitacion.
|
||||
|
||||
## Objetivo
|
||||
|
||||
Mejorar el parser Python para detectar imports anidados. Reducir falsos positivos `unused_in_app_md` a 0 en apps Python que usan paquetes anidados del registry.
|
||||
|
||||
## Arquitectura
|
||||
|
||||
### Archivos afectados
|
||||
|
||||
- `functions/infra/audit_uses_functions.go` — bloque que parsea imports Python.
|
||||
- `functions/infra/audit_uses_functions_test.go` — anadir test cases.
|
||||
- `functions/infra/audit_uses_functions.md` — actualizar `notes` quitando la limitacion.
|
||||
|
||||
## Tareas
|
||||
|
||||
### Fase 1 — extender parser de imports Python
|
||||
1.1 Aceptar regex `^from\s+(\S+)\s+import\s+(.+)` donde grupo 1 puede contener puntos.
|
||||
1.2 Si grupo 1 es `<pkg>` o `<pkg>.<subpkg>` y `<pkg>` matches un dominio Python del registry: para cada simbolo importado en grupo 2, buscar funcion con ese name en el dominio entero (no solo en el subpkg).
|
||||
1.3 Soportar `import <pkg> as <alias>` y posterior `<alias>.<func>(...)` — opcional, dejar como mejora futura si complica.
|
||||
|
||||
### Fase 2 — test cases
|
||||
2.1 `TestAuditUsesFunctions_DetectsNestedImport` — fixture con `from metabase.cards import metabase_get_card`. Verificar `metabase_get_card_py_infra` aparece en imports detectados.
|
||||
2.2 `TestAuditUsesFunctions_NoFalsePositiveOnNested` — fixture con paquete + subpaquete del registry, ningun unused detectado.
|
||||
2.3 `TestAuditUsesFunctions_StarImport` — `from <pkg> import *` debe ignorarse o tratarse como "todo importado" (decision de diseno, documentar).
|
||||
|
||||
### Fase 3 — verificacion en apps reales
|
||||
3.1 Correr `fn doctor uses-functions` post-fix. `apps/auto_metabase` y `apps/metabase_registry` deben quedar sin drift o con drift residual <3 funciones.
|
||||
3.2 Update CHANGELOG.md.
|
||||
|
||||
## Riesgos
|
||||
|
||||
- Falsos positivos invertidos: si el parser acepta cualquier import como uso, reduce el valor del audit. Mitigacion: solo aceptar imports cuyo paquete raiz mapee a un dominio del registry.
|
||||
- Edge case: app importa `from numpy import X` — numpy no es del registry. El parser actual ya lo ignora; mantener.
|
||||
|
||||
## Decisiones de diseno
|
||||
|
||||
- NO portar a AST (`ast.parse`) — overkill para este caso. Regex sobre lineas basta y mantiene la funcion auto-contenida sin spawning Python.
|
||||
- `from <pkg> import *` se documenta como NO soportado (tratado como vacio). Practica recomendada en el registry: nunca star imports.
|
||||
@@ -0,0 +1,63 @@
|
||||
# 0057 — audit_uses_functions: mejorar deteccion de simbolos Go con abreviaturas
|
||||
|
||||
## APP Metadata
|
||||
|
||||
| Campo | Valor |
|
||||
|-------|-------|
|
||||
| **ID** | 0057 |
|
||||
| **Estado** | pendiente |
|
||||
| **Prioridad** | baja |
|
||||
| **Tipo** | enhancement — `functions/infra/audit_uses_functions.go` |
|
||||
|
||||
## Dependencias
|
||||
|
||||
- `audit_uses_functions_go_infra` ya existe.
|
||||
|
||||
## Contexto
|
||||
|
||||
La heuristica Go convierte `name` snake_case a CamelCase para buscar el simbolo exportado en el codigo. La conversion usa `commonAbbrevs` para mapear (ej. `cdp` → `CDP`, `http` → `HTTP`). Pero falla cuando:
|
||||
|
||||
1. La abreviatura no esta en la lista (ej. `cdp_get_html` → `CdpGetHTML` pero codigo usa nombre distinto).
|
||||
2. El simbolo se renombra en la funcion del registry vs el name del frontmatter.
|
||||
|
||||
Caso real (2026-05-07): `cdp_get_html_go_browser` fue marcado `unused_in_app_md` en `script_navegador` aunque `runner.go:126` lo invoca. Se confirmo manualmente como falso positivo.
|
||||
|
||||
## Objetivo
|
||||
|
||||
Reducir falsos positivos en la deteccion de simbolos Go. Dos vias:
|
||||
|
||||
1. Ampliar `commonAbbrevs` con mas terminos comunes en el registry (HTML, CDP, JWT, OAuth, JSON, YAML, SQL, BQ, ID, URL, IP, TCP, TLS, SSH, S3, RBAC).
|
||||
2. Caer a una segunda heuristica: si no encuentra `<CamelCaseName>`, buscar el nombre real exportado leyendo el `.go` de la funcion del registry y extraer `func <Name>(`.
|
||||
|
||||
## Arquitectura
|
||||
|
||||
### Archivos afectados
|
||||
|
||||
- `functions/infra/audit_uses_functions.go` — funcion `snakeToCamel` o equivalente, y bucle de busqueda de simbolos.
|
||||
- `functions/infra/audit_uses_functions_test.go` — anadir tests.
|
||||
|
||||
## Tareas
|
||||
|
||||
### Fase 1 — ampliar commonAbbrevs
|
||||
1.1 Listar funciones del registry con abreviaturas en su `name`: `sqlite3 registry.db "SELECT name FROM functions WHERE lang='go';"` — extraer abreviaturas comunes.
|
||||
1.2 Anadir HTML, CDP, JWT, OAuth, JSON, YAML, SQL, BQ, ID, URL, IP, TCP, TLS, SSH, S3, RBAC a `commonAbbrevs`.
|
||||
1.3 Test `TestSnakeToCamel_HandlesAbbreviations` con todos los nuevos.
|
||||
|
||||
### Fase 2 — fallback a lectura de `.go`
|
||||
2.1 Si la conversion CamelCase no encuentra simbolo, leer `<file_path>.go` de la funcion del registry, extraer primer `func <Name>(` exportado.
|
||||
2.2 Buscar ese nombre en el codigo de la app.
|
||||
2.3 Cachear el mapping (en memoria por ejecucion) para no reabrir el mismo archivo N veces.
|
||||
|
||||
### Fase 3 — verificacion
|
||||
3.1 `cdp_get_html_go_browser` ya NO debe aparecer unused para `script_navegador`.
|
||||
3.2 Correr audit en todas las apps Go, comparar con baseline anterior. Diff de falsos positivos eliminados.
|
||||
|
||||
## Riesgos
|
||||
|
||||
- Lectura de N archivos `.go` ralentiza el audit. Mitigacion: cache + leer solo si la heuristica primaria falla.
|
||||
- Cambio en commonAbbrevs puede romper tests existentes que asumian la conversion antigua. Validar.
|
||||
|
||||
## Decisiones de diseno
|
||||
|
||||
- NO usar `go/parser` — no necesitamos AST completo, basta regex sobre `func [A-Z]\w+(`.
|
||||
- Tampoco cambiar el modelo de "cada funcion del registry tiene un simbolo exportado". Si en el futuro una funcion expone un struct con metodos, anadir manejo.
|
||||
@@ -0,0 +1,60 @@
|
||||
# 0058 — kanban: sync uses_functions cuando termine WIP en curso
|
||||
|
||||
## APP Metadata
|
||||
|
||||
| Campo | Valor |
|
||||
|-------|-------|
|
||||
| **ID** | 0058 |
|
||||
| **Estado** | pendiente |
|
||||
| **Prioridad** | baja |
|
||||
| **Tipo** | docs — `apps/kanban/app.md` |
|
||||
|
||||
## Dependencias
|
||||
|
||||
- Pre-commit hook v2 ya bloqueara commits que toquen codigo de kanban con drift activo.
|
||||
|
||||
## Contexto
|
||||
|
||||
En sesion 2026-05-07 el audit detecto drift en `apps/kanban/app.md`:
|
||||
|
||||
- Missing (en imports, NO en app.md): `password_hash_go_infra`, `password_verify_go_infra`, `session_create_go_infra`, `session_cleanup_go_infra`, `http_session_cookie_middleware_go_infra` (5 funciones, todas relacionadas con auth).
|
||||
- Unused (en app.md, NO en imports detectados): `spa_handler_go_infra`, `sqlite_open_go_infra`, `http_cors_middleware_go_infra` (3 funciones).
|
||||
|
||||
La sincronizacion se aplazo porque el usuario tiene WIP activo en kanban (auth.go, frontend/src/Root.tsx, LoginPage.tsx, etc. — featurea de auth en construccion).
|
||||
|
||||
## Objetivo
|
||||
|
||||
Cuando el WIP de kanban termine y este commiteado:
|
||||
|
||||
1. Confirmar imports reales con `grep '"fn-registry/' apps/kanban/*.go`.
|
||||
2. Sincronizar `app.md` `uses_functions` con la realidad.
|
||||
3. Verificar `fn doctor uses-functions` reporta kanban limpio.
|
||||
|
||||
## Arquitectura
|
||||
|
||||
### Archivos afectados
|
||||
|
||||
- `apps/kanban/app.md` — actualizar array `uses_functions`.
|
||||
|
||||
## Tareas
|
||||
|
||||
### Fase 1 — esperar WIP commiteado
|
||||
1.1 Confirmar `git -C apps/kanban status` limpio.
|
||||
|
||||
### Fase 2 — sincronizar
|
||||
2.1 Listar imports reales: `grep -rh '"fn-registry/' apps/kanban/*.go | sort -u`.
|
||||
2.2 Cruzar con `uses_functions` actual de `app.md`.
|
||||
2.3 Anadir 5 missing si siguen siendo missing.
|
||||
2.4 Quitar 3 unused si siguen sin usarse (cuidado: el WIP nuevo puede haberlas activado o desactivado otras).
|
||||
|
||||
### Fase 3 — verificar
|
||||
3.1 `fn index`.
|
||||
3.2 `fn doctor uses-functions` debe reportar `kanban_go_tools` sin drift.
|
||||
|
||||
## Riesgos
|
||||
|
||||
- El WIP cambia el conjunto de drift original. Re-correr audit antes de aplicar cambios — no asumir que las 5+3 detectadas el 2026-05-07 son aun validas.
|
||||
|
||||
## Decisiones de diseno
|
||||
|
||||
- Issue trivial pero se documenta para no olvidar (el pre-commit hook ya lo bloquearia, asi que no es urgente — solo corrige fricciones de UX).
|
||||
@@ -0,0 +1,96 @@
|
||||
# 0059 — Resolver doble tracking de `apps/*/app.md` (fn_registry + sub-repo)
|
||||
|
||||
## APP Metadata
|
||||
|
||||
| Campo | Valor |
|
||||
|-------|-------|
|
||||
| **ID** | 0059 |
|
||||
| **Estado** | pendiente |
|
||||
| **Prioridad** | media |
|
||||
| **Tipo** | infra — git, .gitignore, indexer |
|
||||
|
||||
## Dependencias
|
||||
|
||||
- ADR 0002 (apps_analyses_as_dataforge_master): cada app es su propio repo.
|
||||
- `.gitignore` raiz: `apps/*/`.
|
||||
|
||||
## Contexto
|
||||
|
||||
Detectado en sesion 2026-05-07:
|
||||
|
||||
- `.gitignore` de `fn_registry` excluye `apps/*/`.
|
||||
- Pero `apps/dag_engine/app.md` aparece tracked tambien por `fn_registry` (legado pre-gitignore).
|
||||
- Resultado: el mismo archivo fisico es tracked por DOS repos: `fn_registry` Y `dataforge/dag_engine` (sub-repo).
|
||||
- Cualquier cambio crea conmits duplicados, status confuso, riesgo de divergencia.
|
||||
|
||||
```
|
||||
$ git status # en fn_registry
|
||||
M apps/dag_engine/app.md
|
||||
$ git -C apps/dag_engine status
|
||||
M app.md
|
||||
```
|
||||
|
||||
Mismo archivo. Dos `git add` distintos.
|
||||
|
||||
## Objetivo
|
||||
|
||||
Eliminar el doble tracking. Decidir source of truth y limpiar la otra.
|
||||
|
||||
## Decisiones a tomar
|
||||
|
||||
**Opcion A: source of truth = sub-repo.**
|
||||
- `git rm --cached apps/*/app.md` en fn_registry (sin borrar archivo).
|
||||
- `app.md` solo se commitea desde el sub-repo.
|
||||
- `fn index` lee desde disco igual.
|
||||
- PRO: consistente con ADR 0002 (sub-repo es la unidad).
|
||||
- CONTRA: `app.md` no se versiona junto con cambios al registry que lo rompan (ej. funciones referenciadas que se borran).
|
||||
|
||||
**Opcion B: source of truth = fn_registry.**
|
||||
- Sub-repo NO trackea `app.md` (anadir a su `.gitignore`).
|
||||
- `fn_registry` lo versiona.
|
||||
- PRO: el indexer y el registry tienen control directo.
|
||||
- CONTRA: el sub-repo es incompleto (falta su propia ficha de identidad).
|
||||
|
||||
**Opcion C: ambos lo trackean conscientemente.**
|
||||
- Documentar en regla nueva.
|
||||
- Hook que bloquea desync (post-commit en uno avisa para commitear en el otro).
|
||||
- PRO: cada repo es self-describing.
|
||||
- CONTRA: complejidad operacional alta, riesgo de drift.
|
||||
|
||||
**Recomendada: Opcion A.** Alinea con ADR 0002. La cobertura "registry rompe app.md" se cubre con `fn doctor uses-functions` + pre-commit hook v2.
|
||||
|
||||
## Arquitectura
|
||||
|
||||
### Archivos afectados
|
||||
|
||||
- `.gitignore` raiz — verificar que `apps/*/` cubre todo.
|
||||
- Posiblemente otros `apps/*/app.md` tracked legacy (auditar).
|
||||
- `docs/adr/0004-app-md-source-of-truth.md` — NUEVO ADR.
|
||||
|
||||
## Tareas
|
||||
|
||||
### Fase 1 — auditar
|
||||
1.1 `git ls-files apps/ | grep app.md` — listar todos los `app.md` tracked en fn_registry.
|
||||
1.2 Cruzar con sub-repos para confirmar duplicacion.
|
||||
|
||||
### Fase 2 — decision (humano)
|
||||
2.1 Confirmar Opcion A o cambiar a B/C con razon documentada.
|
||||
|
||||
### Fase 3 — implementacion (Opcion A)
|
||||
3.1 Para cada `app.md` duplicado: confirmar que existe identico en el sub-repo.
|
||||
3.2 `git rm --cached apps/<name>/app.md` en fn_registry.
|
||||
3.3 Commit limpio en fn_registry.
|
||||
3.4 No tocar el sub-repo (ya esta correcto).
|
||||
|
||||
### Fase 4 — ADR + docs
|
||||
4.1 Crear `docs/adr/0004-app-md-source-of-truth.md` con la decision y razon.
|
||||
4.2 Actualizar `.claude/rules/cpp_apps.md` y `apps_vs_functions.md` si mencionan tracking.
|
||||
|
||||
## Riesgos
|
||||
|
||||
- Si el indexer asume que `app.md` esta tracked en fn_registry (no es el caso, lee de disco), cero impacto.
|
||||
- Si `fn sync` o `pc_locations` asumen tracking, validar que solo dependen del archivo fisico.
|
||||
|
||||
## Decisiones de diseno
|
||||
|
||||
- Opcion A es coherente con ADR 0002 — apps son sub-repos completos.
|
||||
@@ -0,0 +1,80 @@
|
||||
# 0060 — `fn doctor secrets`: scan de secrets en TODOS los repos
|
||||
|
||||
## APP Metadata
|
||||
|
||||
| Campo | Valor |
|
||||
|-------|-------|
|
||||
| **ID** | 0060 |
|
||||
| **Estado** | pendiente |
|
||||
| **Prioridad** | media |
|
||||
| **Tipo** | feature — `cmd/fn/doctor.go` + funcion del registry |
|
||||
|
||||
## Dependencias
|
||||
|
||||
- `scan_secrets_in_dirty_bash_cybersecurity` ya existe (escanea solo dirty trees por nombres sospechosos).
|
||||
- `discover_git_repos_bash_infra` ya existe.
|
||||
- Pre-commit hook v2 invoca `scan_secrets_in_dirty` por repo.
|
||||
|
||||
## Contexto
|
||||
|
||||
Hoy el escaneo de secrets ocurre solo:
|
||||
|
||||
1. En el pre-commit hook (de cada repo, sobre dirty tree antes del commit).
|
||||
2. Cuando el usuario invoca manualmente `scan_secrets_in_dirty.sh`.
|
||||
|
||||
NO hay un audit global "scan TODOS los repos en una pasada" para detectar secrets que ya esten commiteados (caso peor) o staged en repos que no se commitearon hoy. Riesgo: una key olvidada en un repo viejo puede estar pushed a Gitea desde hace meses sin que nadie lo sepa.
|
||||
|
||||
## Objetivo
|
||||
|
||||
Anadir subcomando `fn doctor secrets` que:
|
||||
|
||||
1. Itera TODOS los repos descubiertos por `discover_git_repos`.
|
||||
2. Por cada uno, escanea TODO el HEAD (no solo dirty) buscando:
|
||||
- Nombres sospechosos (`*.env`, `*credentials*`, `*.key`, `*.pem`, `id_rsa*`, `*secret*`, `*token*.txt`).
|
||||
- Patterns en contenido: AWS keys (`AKIA...`), JWT tokens, GitHub tokens (`ghp_...`), Google API keys (`AIza...`).
|
||||
3. Reporta hallazgos como en otros `fn doctor` (texto humano + `--json`).
|
||||
4. Exit 0 si limpio, 1 si encuentra algo.
|
||||
|
||||
## Arquitectura
|
||||
|
||||
### Archivos afectados
|
||||
|
||||
- NUEVA funcion `scan_secrets_repo_bash_cybersecurity` (`bash/functions/cybersecurity/scan_secrets_repo.sh` + `.md`) — version "todo el repo" del existente.
|
||||
- NUEVA funcion `scan_secrets_all_repos_go_cybersecurity` (`functions/cybersecurity/scan_secrets_all_repos.go`) — orquestador Go que itera repos y compone resultado.
|
||||
- `cmd/fn/doctor.go` — anadir subcomando `secrets` que invoca la funcion Go.
|
||||
- `.claude/rules/fn_doctor.md` — anadir entrada para `secrets`.
|
||||
|
||||
## Tareas
|
||||
|
||||
### Fase 1 — funcion bash de scan completo
|
||||
1.1 Crear `scan_secrets_repo_bash_cybersecurity`:
|
||||
- Args: `<repo_dir>`.
|
||||
- Lista todos los archivos tracked por git (`git ls-files`).
|
||||
- Para cada uno, aplica los filtros de nombre y luego `grep -E` patterns en contenido.
|
||||
- Output: lineas `SECRET <type> <repo>:<file>:<line> <pattern_match>`.
|
||||
- Exit 0 si limpio, 1 si hay matches.
|
||||
|
||||
### Fase 2 — orquestador Go
|
||||
2.1 `ScanSecretsAllRepos(registryRoot string) ([]SecretFinding, error)`.
|
||||
2.2 Llama internamente `discover_git_repos` (via shell-out o portar a Go).
|
||||
2.3 Por cada repo, ejecuta `scan_secrets_repo.sh` y agrega findings.
|
||||
2.4 Test con repo temporal con archivo dummy `.env`.
|
||||
|
||||
### Fase 3 — CLI + docs
|
||||
3.1 Anadir case `secrets` a `cmd/fn/doctor.go`.
|
||||
3.2 Texto humano: tabla `REPO | FILE | TYPE | MATCH`.
|
||||
3.3 `--json`: array de findings.
|
||||
3.4 Anadir a `fn doctor` (todos los checks).
|
||||
3.5 Actualizar `.claude/rules/fn_doctor.md` y CHANGELOG.
|
||||
|
||||
## Riesgos
|
||||
|
||||
- False positives en repos con muchos archivos. Mitigacion: aplicar filtros estrictos, opcion `--ignore-file` con regex.
|
||||
- Lentitud: escanear todos los `git ls-files` de 32 sub-repos puede tardar segundos. Mitigacion: paralelizar por repo (goroutines).
|
||||
- Si encuentra secret real, exponerlo en stdout es contradictorio. Mitigacion: redactar el match (`AKIA****REDACTED****`) en output.
|
||||
|
||||
## Decisiones de diseno
|
||||
|
||||
- Mantener la deteccion bash (scan_secrets_repo) — es lo que usan los hooks. El orquestador Go solo agrega.
|
||||
- Patterns hardcodeados al principio. Despues mover a archivo de config si crecen.
|
||||
- NO integrar gitleaks/trufflehog — aumenta deps externas. Los patterns basicos cubren 95% de casos.
|
||||
@@ -0,0 +1,79 @@
|
||||
# 0061 — Integrar `notify_telegram` en deploy_server + bucle reactivo
|
||||
|
||||
## APP Metadata
|
||||
|
||||
| Campo | Valor |
|
||||
|-------|-------|
|
||||
| **ID** | 0061 |
|
||||
| **Estado** | pendiente |
|
||||
| **Prioridad** | media |
|
||||
| **Tipo** | integration — `apps/deploy_server/`, `fn_operations/` |
|
||||
|
||||
## Dependencias
|
||||
|
||||
- `notify_telegram_go_infra` creada el 2026-05-07.
|
||||
- `pass` con bot token guardado (`pass insert telegram/bot_token`).
|
||||
- `pass` con chat_id (`pass insert telegram/chat_id`).
|
||||
- `apps/deploy_server` (issue 0054 paralelo — refactor registry-first).
|
||||
- `fn_operations/operations.go::ExecuteAndReact()` (bucle reactivo Go).
|
||||
|
||||
## Contexto
|
||||
|
||||
`notify_telegram_go_infra` fue creada como funcion atomica pero no esta integrada en ningun consumidor. El bucle reactivo (`assertions` que fallan) y los deploys (deploy_server) son los dos puntos donde alertas reales tendrian valor inmediato:
|
||||
|
||||
- **deploy_server**: hoy si un deploy falla solo queda en `deploy_logs`. El usuario tiene que mirar la BD o la TUI para enterarse. Ideal: notify_telegram con `[FAIL] <app>@<host>: <error>`.
|
||||
- **bucle reactivo**: assertion `critical` falla → corruption detectada en datos. Hoy solo se persiste en `assertion_results`. Ideal: notify_telegram con `[CRITICAL] <entity>: <rule>: <value> (expected <expected>)`.
|
||||
|
||||
## Objetivo
|
||||
|
||||
Anadir hooks de notificacion en los dos puntos:
|
||||
|
||||
1. `deploy_server` envia notify al final de cada deploy (success o fail).
|
||||
2. `fn_operations.ExecuteAndReact` envia notify cuando una assertion `critical` falla.
|
||||
|
||||
Ambos hooks usan `notify_telegram_go_infra` y leen credenciales de `pass`.
|
||||
|
||||
## Arquitectura
|
||||
|
||||
### Archivos afectados
|
||||
|
||||
- `apps/deploy_server/deployer.go` — anadir post-deploy hook que invoca notify.
|
||||
- `apps/deploy_server/app.md` — declarar `notify_telegram_go_infra` en uses_functions.
|
||||
- `fn_operations/operations.go` — extender `ExecuteAndReact` con notify hook.
|
||||
- `fn_operations/operations_test.go` — test que mockea notify.
|
||||
- NUEVA funcion `pass_telegram_creds_bash_infra` o helper Go para leer pass entries.
|
||||
|
||||
## Tareas
|
||||
|
||||
### Fase 1 — credenciales desde pass
|
||||
1.1 Decidir naming: `pass insert telegram/bot_token` y `pass insert telegram/chat_id`.
|
||||
1.2 Helper para leer ambas (existe `pass_get_bash_infra`, basta invocarlo).
|
||||
1.3 Documentar setup en `docs/sync_setup.md` (no commitear values).
|
||||
|
||||
### Fase 2 — integracion deploy_server
|
||||
2.1 En `deployer.go` post-deploy: si `deploy_telegram_enabled = true` (config en `deploy_targets`), construir mensaje y llamar `infra.NotifyTelegram(...)`.
|
||||
2.2 Truncar mensaje a 4096 chars (la funcion ya lo hace, pero documentar).
|
||||
2.3 Schema de `deploy_targets`: anadir columna `notify_telegram BOOLEAN DEFAULT false`.
|
||||
2.4 CLI: `deploy_server target add ... --notify-telegram`.
|
||||
|
||||
### Fase 3 — integracion bucle reactivo
|
||||
3.1 En `ExecuteAndReact`, tras evaluar assertions, si alguna `critical` fallo, construir mensaje y llamar notify.
|
||||
3.2 Config: `assertion.notify_telegram BOOLEAN` (por assertion) — solo notifica si true.
|
||||
3.3 Test `TestExecuteAndReact_NotifiesCriticalFailure` con notify mockeado.
|
||||
|
||||
### Fase 4 — docs + verificacion
|
||||
4.1 Update CHANGELOG.md.
|
||||
4.2 Manual test: forzar un deploy fail, verificar mensaje llega.
|
||||
4.3 Manual test: forzar assertion fail, verificar mensaje llega.
|
||||
|
||||
## Riesgos
|
||||
|
||||
- Spam de notificaciones si una assertion falla repetidamente. Mitigacion: rate limiting (no enviar si ya se envio en ultima hora) — opcional, dejar para v2.
|
||||
- Token expuesto en logs si `notify_telegram` lo loggea. Verificar que la funcion redacta el token.
|
||||
- Sin pass: la integracion debe degradar silenciosa (log warning, no abortar deploy).
|
||||
|
||||
## Decisiones de diseno
|
||||
|
||||
- Mensajes en formato `[<level>] <subject>: <body>` para grep facil en chat.
|
||||
- Markdown opcional (parseMode "Markdown") — abre superficie a inyeccion de markdown si el body viene de error externo. Default `parseMode=""` (plain).
|
||||
- NO crear topic/thread de Telegram — un solo chat para todo. Si crece, refactor.
|
||||
@@ -0,0 +1,79 @@
|
||||
# 0062 — Politica de deprecacion para funciones del registry sin consumidores
|
||||
|
||||
## APP Metadata
|
||||
|
||||
| Campo | Valor |
|
||||
|-------|-------|
|
||||
| **ID** | 0062 |
|
||||
| **Estado** | pendiente |
|
||||
| **Prioridad** | baja |
|
||||
| **Tipo** | research + policy — `.claude/rules/`, `docs/` |
|
||||
|
||||
## Dependencias
|
||||
|
||||
- `find_unused_functions_go_infra` (existe, lista 704 funciones sin consumidores al 2026-05-07).
|
||||
- `fn doctor unused`.
|
||||
|
||||
## Contexto
|
||||
|
||||
Sesion 2026-05-07: el registry tiene 1066 funciones. `fn doctor unused` reporta 704 sin consumidores (66%). La mayoria son utilities core puras (`compose2_go_core`, `curry2_go_core`, `chunk_go_core`, `flat_map_slice_go_core`, etc.) construidas especulativamente — esperando que alguna app las consuma.
|
||||
|
||||
Sin politica explicita de "que hacer con unused", el registry crece sin freno. Posibles destinos:
|
||||
|
||||
1. **Mantener** indefinidamente (libreria publica disponible).
|
||||
2. **Deprecar via tag** (`tags: [deprecated]`) — sigue presente pero senala "no usar para codigo nuevo".
|
||||
3. **Borrar** despues de N meses sin consumidor.
|
||||
|
||||
Decision pospuesta: cualquier eleccion afecta cientos de archivos y la velocidad de scaffold de nuevas apps que pueden recogerlas.
|
||||
|
||||
## Objetivo
|
||||
|
||||
Definir y documentar una politica formal:
|
||||
|
||||
1. Criterios cuantitativos: cuanto tiempo (en dias) sin consumidor justifica deprecar.
|
||||
2. Excepciones: funciones con tag `core-utility` o `library-quality` se mantienen.
|
||||
3. Workflow de deprecacion: tag → 90 dias → borrar.
|
||||
4. Hook automatico: `fn doctor unused --propose-deprecation` abre proposals.
|
||||
|
||||
## Arquitectura
|
||||
|
||||
### Archivos afectados
|
||||
|
||||
- NUEVA regla `.claude/rules/unused_functions.md`.
|
||||
- NUEVO ADR `docs/adr/0005-unused-functions-policy.md`.
|
||||
- `find_unused_functions_go_infra` — opcionalmente extender con `AgeDays` desde `updated_at` (ya lo tiene) y filtrar por edad.
|
||||
- `cmd/fn/doctor.go` — anadir flag `--older-than <days>` al subcomando `unused`.
|
||||
|
||||
## Tareas
|
||||
|
||||
### Fase 1 — definir politica (humano)
|
||||
1.1 Decidir umbrales: `tag deprecated` tras 60 dias sin consumidor; `borrar` tras 180 dias.
|
||||
1.2 Decidir excepciones: tag `core-utility` exime, tag `library-quality` exime, dominios `core` puros mas tolerantes que dominios infra.
|
||||
1.3 Decidir si la deprecacion es manual (humano via proposal) o automatica (cron).
|
||||
|
||||
### Fase 2 — escribir ADR + regla
|
||||
2.1 ADR 0005 con la decision, alternativas, consecuencias.
|
||||
2.2 Regla `.claude/rules/unused_functions.md` operacional.
|
||||
2.3 Update `INDEX.md`.
|
||||
|
||||
### Fase 3 — extender herramienta
|
||||
3.1 `fn doctor unused --older-than 60` filtra por edad.
|
||||
3.2 `fn doctor unused --propose-deprecation` crea proposals automaticas con `kind=deprecate_function`.
|
||||
3.3 Workflow humano: revisar proposals, aprobar, agente aplica el tag.
|
||||
|
||||
### Fase 4 — primera ronda
|
||||
4.1 Correr `fn doctor unused --older-than 90`.
|
||||
4.2 Decidir caso por caso (o lote por dominio): mantener / deprecar / borrar.
|
||||
4.3 Aplicar tags. Re-indexar. Update CHANGELOG.
|
||||
|
||||
## Riesgos
|
||||
|
||||
- Borrar funciones que el usuario planeaba usar pronto. Mitigacion: ventana larga (180 dias) + proposal manual antes de borrar.
|
||||
- Tags desfasados: una funcion deprecated puede seguir siendo usada. Mitigacion: el indexer puede warn si una app declara una `deprecated` en `uses_functions`.
|
||||
- Deprecation como excusa para no usar (cosmica). Mitigacion: revisiones trimestrales, no que se acumule.
|
||||
|
||||
## Decisiones de diseno
|
||||
|
||||
- NO borrar nunca automaticamente. Borrado siempre humano via PR/proposal aprobada.
|
||||
- Tag `deprecated` es el verbo automatizable: un agente puede aplicarlo via proposal.
|
||||
- Para funciones nuevas creadas tras adoptar la politica, exigir que tengan al menos UN consumidor previsto al merge — sino van directo con tag `experimental`.
|
||||
@@ -69,3 +69,12 @@
|
||||
| [0050](0050-jupyter-exec-collab-client-failure.md) | `jupyter_exec` falla por cliente colaborativo (workaround documentado) | pendiente | media | bug | — |
|
||||
| [0051](0051-extraction-pipeline-followups.md) | Funciones pendientes del pipeline NER+RE (NuExtract, extract_graph_from_pdf, spaCy ES V2, kernel startup fix, REBEL EN) | pendiente | media | feature | — |
|
||||
| [0053](completed/0053-kanban-chat-panel.md) | Chat lateral en apps/kanban via `claude -p` (sonnet, persistencia localStorage) | completado | media | feature | — |
|
||||
| [0054](0054-deploy-server-registry-first-refactor.md) | deploy_server: refactor registry-first (SSH/systemd/rsync inline → registry funcs) | pendiente | alta | refactor | — |
|
||||
| [0055](0055-docker-tui-registry-first-refactor.md) | docker_tui: refactor para usar funciones docker_* del registry | pendiente | alta | refactor | — |
|
||||
| [0056](0056-audit-python-nested-imports.md) | audit_uses_functions: detectar imports Python anidados (`from pkg.subpkg import X`) | pendiente | media | enhancement | — |
|
||||
| [0057](0057-audit-go-symbol-naming.md) | audit_uses_functions: mejorar deteccion de simbolos Go con abreviaturas | pendiente | baja | enhancement | — |
|
||||
| [0058](0058-kanban-uses-functions-sync.md) | kanban: sync uses_functions cuando termine WIP en curso | pendiente | baja | docs | — |
|
||||
| [0059](0059-nested-app-md-tracking.md) | Resolver doble tracking de `apps/*/app.md` (fn_registry + sub-repo) | pendiente | media | infra | — |
|
||||
| [0060](0060-fn-doctor-secrets-subcommand.md) | `fn doctor secrets`: scan de secrets en TODOS los repos | pendiente | media | feature | — |
|
||||
| [0061](0061-notify-telegram-integration.md) | Integrar `notify_telegram` en deploy_server + bucle reactivo | pendiente | media | integration | 0054 |
|
||||
| [0062](0062-deprecate-unused-core-functions.md) | Politica de deprecacion para funciones del registry sin consumidores | pendiente | baja | research | — |
|
||||
|
||||
Reference in New Issue
Block a user