fad4006f60
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
570 lines
22 KiB
Markdown
570 lines
22 KiB
Markdown
---
|
|
id: "0022"
|
|
title: "Init Pipelines"
|
|
status: completado
|
|
type: feature
|
|
domain: []
|
|
scope: multi-app
|
|
priority: alta
|
|
depends: []
|
|
blocks: []
|
|
related: []
|
|
created: 2026-05-17
|
|
updated: 2026-05-17
|
|
tags: []
|
|
---
|
|
# 0022 — Init Pipelines
|
|
|
|
## Metadata
|
|
|
|
| Campo | Valor |
|
|
|-------|-------|
|
|
| **ID** | 0022 |
|
|
| **Estado** | pendiente |
|
|
| **Prioridad** | alta |
|
|
| **Tipo** | feature |
|
|
|
|
## Dependencias
|
|
|
|
| ID | Titulo | Estado | Requerido |
|
|
|----|--------|--------|-----------|
|
|
| 0009 | HTTP Server Foundation | pendiente | si |
|
|
| 0010 | Auth System | pendiente | si |
|
|
| 0015 | Database Migrations | pendiente | si |
|
|
|
|
**Bloqueada por:** `#0009` (http_serve, http_router, http_json_response, http_middleware_chain), `#0010` (jwt_middleware, password_hash, session_create), `#0015` (migration_create, migration_up, migration_status). Los pipelines de init generan boilerplate que importa y compone estas funciones — sin ellas, el codigo scaffoldeado no compilaria.
|
|
|
|
**Desbloquea:** cualquier app nueva del registry se puede crear con un solo comando en vez de copiar y adaptar una app existente.
|
|
|
|
---
|
|
|
|
## Objetivo
|
|
|
|
Cuatro bash pipelines que scaffold apps completas en `apps/` con un solo comando. Cada uno genera la estructura de directorios, archivos boilerplate, `app.md` con frontmatter correcto, y verifica que el resultado compila. Misma filosofia que `init_jupyter_analysis_bash_pipelines`: componer funciones atomicas del registry para producir un entorno listo para trabajar.
|
|
|
|
## Contexto
|
|
|
|
- Existen tres init pipelines: `init_go_project_bash_pipelines` (repo Go generico), `init_go_module_bash_pipelines` (modulo Go simple), `init_jupyter_analysis_bash_pipelines` (analysis Jupyter). Todos scaffoldean estructuras basicas.
|
|
- **No existe ningun pipeline para scaffoldear apps del registry** con HTTP server, auth, DB, frontend, Wails o TUI. Cada app nueva se construye copiando otra y adaptando manualmente.
|
|
- Las apps existentes (`deploy_server`, `sqlite_api`, `rapid_dashboards`, `pipeline_launcher`) comparten patrones repetitivos: main.go con graceful shutdown, config desde env vars, health check, migrations, app.md.
|
|
- Con las funciones de 0009 (HTTP), 0010 (auth) y 0015 (migrations) disponibles, el boilerplate de una app API es predecible y automatizable.
|
|
- El registry ya tiene funciones Wails completas (`scaffold_wails_app_go_infra`, `install_wails_bash_infra`, `wails_build_go_infra`, hooks `use_wails_*_ts_ui`, `wails_provider_ts_ui`) y TUI (`new_base_model_go_tui`, `run_fullscreen_go_tui`, temas, spinners, listas).
|
|
|
|
## Arquitectura
|
|
|
|
```
|
|
bash/functions/pipelines/
|
|
├── init_api_app.sh — NEW: scaffold Go HTTP API app
|
|
├── init_api_app.md — NEW
|
|
├── init_web_app.sh — NEW: scaffold full-stack app (Go API + React)
|
|
├── init_web_app.md — NEW
|
|
├── init_desktop_app.sh — NEW: scaffold Wails desktop app
|
|
├── init_desktop_app.md — NEW
|
|
├── init_cli_app.sh — NEW: scaffold Go CLI/TUI app
|
|
├── init_cli_app.md — NEW
|
|
```
|
|
|
|
Todas son `kind: pipeline`, `purity: impure`, `lang: bash`, `domain: pipelines`.
|
|
|
|
### Patron de composicion
|
|
|
|
Cada pipeline sigue el mismo patron que `init_jupyter_analysis`:
|
|
|
|
1. Source funciones atomicas del registry via `source "$REGISTRY_ROOT/bash/functions/..."`
|
|
2. Parsear argumentos (nombre obligatorio, flags opcionales)
|
|
3. Crear estructura de directorios con `mkdir -p`
|
|
4. Escribir archivos boilerplate con heredocs
|
|
5. Generar `app.md` con frontmatter correcto
|
|
6. Ejecutar `fn index` para registrar la app
|
|
7. Verificar con `go vet` / `pnpm build` / `wails build` segun corresponda
|
|
|
|
---
|
|
|
|
## Diseno
|
|
|
|
### Pipeline 1: `init_api_app`
|
|
|
|
Scaffold de Go HTTP API app en `apps/`.
|
|
|
|
**Uso:**
|
|
|
|
```bash
|
|
fn run init_api_app my_service
|
|
fn run init_api_app my_service --port 8080 --with-auth --with-db
|
|
```
|
|
|
|
**Archivos generados:**
|
|
|
|
```
|
|
apps/{nombre}/
|
|
├── main.go — Entry point: config → router → middleware → http_serve con graceful shutdown
|
|
├── handlers.go — Handler GET /health + handler de ejemplo GET /api/v1/status
|
|
├── config.go — Struct Config con tags + carga desde .env / env vars
|
|
├── migrations/
|
|
│ └── 001_initial.sql — CREATE TABLE ejemplo con id, created_at, updated_at
|
|
├── app.md — Frontmatter con tag service, uses_functions, dir_path
|
|
├── Makefile — Targets: build, run, test, vet, clean
|
|
├── .env.example — Variables de entorno documentadas (PORT, DB_PATH, etc.)
|
|
└── .gitignore — Binario, .env, *.db-shm, *.db-wal
|
|
```
|
|
|
|
**Funciones del registry compuestas:**
|
|
|
|
| Funcion | Para que |
|
|
|---------|---------|
|
|
| `assert_command_exists_bash_shell` | Verificar que `go` esta instalado |
|
|
| `http_serve_go_infra` (0009) | Codigo de graceful shutdown en main.go |
|
|
| `http_router_go_infra` (0009) | Registro de rutas en main.go |
|
|
| `http_json_response_go_infra` (0009) | Helper en handlers.go |
|
|
| `http_error_response_go_infra` (0009) | Helper en handlers.go |
|
|
| `http_middleware_chain_go_infra` (0009) | Composicion de middlewares en main.go |
|
|
| `http_logger_middleware_go_infra` (0009) | Logging en main.go |
|
|
| `http_cors_middleware_go_infra` (0009) | CORS en main.go |
|
|
| `migration_up_go_infra` (0015) | Aplicar migrations en main.go al arrancar |
|
|
| `config_load_go_infra` (0018) | Carga de config en config.go (si existe) |
|
|
|
|
**Flags opcionales:**
|
|
|
|
| Flag | Efecto |
|
|
|------|--------|
|
|
| `--port N` | Puerto por defecto en config y .env.example (default: 8080) |
|
|
| `--with-auth` | Anade jwt_middleware, handlers de login/register, tabla users en migration |
|
|
| `--with-db` | Anade operations.db setup, store.go con helpers CRUD basicos |
|
|
| `--with-ops` | Anade `fn ops init` para crear operations.db con schema completo |
|
|
|
|
**main.go generado (esquema):**
|
|
|
|
```go
|
|
package main
|
|
|
|
import (
|
|
"context"
|
|
"log"
|
|
"os"
|
|
"os/signal"
|
|
|
|
"fn_registry/functions/infra"
|
|
)
|
|
|
|
func main() {
|
|
cfg := LoadConfig()
|
|
|
|
// Migrations
|
|
if err := infra.MigrationUp(cfg.DBPath, "migrations"); err != nil {
|
|
log.Fatal(err)
|
|
}
|
|
|
|
// Routes
|
|
routes := []infra.Route{
|
|
{Method: "GET", Path: "/health", Handler: healthHandler},
|
|
{Method: "GET", Path: "/api/v1/status", Handler: statusHandler},
|
|
}
|
|
mux := infra.HttpRouter(routes)
|
|
|
|
// Middleware
|
|
middleware := infra.HttpMiddlewareChain(
|
|
infra.HttpCorsMiddleware(cfg.CORSOrigins, []string{"GET", "POST", "PUT", "DELETE"}),
|
|
infra.HttpLoggerMiddleware(os.Stdout),
|
|
)
|
|
|
|
// Serve
|
|
ctx, cancel := signal.NotifyContext(context.Background(), os.Interrupt)
|
|
defer cancel()
|
|
|
|
log.Printf("starting %s on :%s", cfg.AppName, cfg.Port)
|
|
if err := infra.HttpServe(":"+cfg.Port, middleware(mux), ctx); err != nil {
|
|
log.Fatal(err)
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### Pipeline 2: `init_web_app`
|
|
|
|
Scaffold de full-stack app: Go API backend + React frontend con Mantine.
|
|
|
|
**Uso:**
|
|
|
|
```bash
|
|
fn run init_web_app my_dashboard
|
|
fn run init_web_app my_dashboard --port 8080 --with-auth
|
|
```
|
|
|
|
**Archivos generados:**
|
|
|
|
```
|
|
apps/{nombre}/
|
|
├── main.go — Igual que init_api_app + serve static files del frontend build
|
|
├── handlers.go — Health + API handlers de ejemplo
|
|
├── config.go — Config con FRONTEND_DIR
|
|
├── migrations/
|
|
│ └── 001_initial.sql
|
|
├── app.md — tag service, uses frontend
|
|
├── Makefile — Targets: build, build-frontend, run, dev, test, clean
|
|
├── .env.example
|
|
├── .gitignore
|
|
├── docker-compose.yml — Dev: Go API hot-reload + frontend dev server
|
|
└── frontend/
|
|
├── package.json — pnpm, vite, react, @mantine/core, @mantine/charts, @fn_library
|
|
├── vite.config.ts — API proxy a localhost:${port}
|
|
├── tsconfig.json
|
|
├── index.html
|
|
├── postcss.config.cjs
|
|
└── src/
|
|
├── main.tsx — FnMantineProvider + App mount
|
|
├── App.tsx — Router basico con pagina de ejemplo
|
|
├── theme.ts — createTheme() con colores del proyecto
|
|
└── pages/
|
|
└── Home.tsx — Pagina de ejemplo usando crud_page_ts_ui o dashboard_layout_ts_ui
|
|
```
|
|
|
|
**Funciones adicionales compuestas (sobre init_api_app):**
|
|
|
|
| Funcion | Para que |
|
|
|---------|---------|
|
|
| `mantine_provider_ts_ui` | Provider raiz en main.tsx |
|
|
| `crud_page_ts_ui` | Pagina de ejemplo funcional |
|
|
| `app_shell_ts_ui` | Layout con navbar y header |
|
|
| `data_table_ts_ui` | Tabla de datos en la pagina de ejemplo |
|
|
|
|
**vite.config.ts generado:**
|
|
|
|
```ts
|
|
import { defineConfig } from "vite";
|
|
import react from "@vitejs/plugin-react";
|
|
import path from "path";
|
|
|
|
export default defineConfig({
|
|
plugins: [react()],
|
|
resolve: {
|
|
alias: {
|
|
"@fn_library": path.resolve(__dirname, "../../frontend/functions/ui"),
|
|
},
|
|
},
|
|
server: {
|
|
proxy: {
|
|
"/api": {
|
|
target: "http://localhost:${PORT}",
|
|
changeOrigin: true,
|
|
},
|
|
"/health": {
|
|
target: "http://localhost:${PORT}",
|
|
},
|
|
},
|
|
},
|
|
});
|
|
```
|
|
|
|
**docker-compose.yml generado:**
|
|
|
|
```yaml
|
|
services:
|
|
api:
|
|
build: .
|
|
ports:
|
|
- "${PORT}:${PORT}"
|
|
env_file: .env
|
|
volumes:
|
|
- ./migrations:/app/migrations
|
|
frontend:
|
|
image: node:20-alpine
|
|
working_dir: /app
|
|
command: sh -c "corepack enable && pnpm install && pnpm dev"
|
|
ports:
|
|
- "5173:5173"
|
|
volumes:
|
|
- ./frontend:/app
|
|
```
|
|
|
|
---
|
|
|
|
### Pipeline 3: `init_desktop_app`
|
|
|
|
Scaffold de Wails desktop app con Go backend y React frontend con @fn_library.
|
|
|
|
**Uso:**
|
|
|
|
```bash
|
|
fn run init_desktop_app my_tool
|
|
fn run init_desktop_app my_tool --with-db
|
|
```
|
|
|
|
**Archivos generados:**
|
|
|
|
```
|
|
apps/{nombre}/
|
|
├── main.go — Wails entry point con embed del frontend
|
|
├── app.go — Struct App con bindings base (Greet, GetVersion)
|
|
├── wails.json — Config Wails apuntando a frontend/
|
|
├── go.mod
|
|
├── app.md — framework: wails, uses wails hooks
|
|
├── .gitignore
|
|
└── frontend/
|
|
├── package.json — pnpm, vite, react, @mantine/core, @fn_library
|
|
├── vite.config.ts
|
|
├── tsconfig.json
|
|
├── index.html
|
|
└── src/
|
|
├── main.tsx — WailsProvider + FnMantineProvider + App
|
|
├── App.tsx — Ejemplo usando useWailsQuery + data_table
|
|
└── theme.ts — createTheme()
|
|
```
|
|
|
|
**Funciones del registry compuestas:**
|
|
|
|
| Funcion | Para que |
|
|
|---------|---------|
|
|
| `scaffold_wails_app_go_infra` | Genera estructura base Wails (main.go, app.go, wails.json, go.mod) |
|
|
| `install_wails_bash_infra` | Verifica/instala Wails CLI y deps de sistema |
|
|
| `wails_provider_ts_ui` | Provider React para IPC cache |
|
|
| `use_wails_query_ts_ui` | Hook de ejemplo en App.tsx |
|
|
| `mantine_provider_ts_ui` | Provider Mantine |
|
|
| `wails_bind_crud_go_infra` | Genera bindings CRUD si `--with-db` |
|
|
|
|
**Flags opcionales:**
|
|
|
|
| Flag | Efecto |
|
|
|------|--------|
|
|
| `--with-db` | Anade SQLite con migrations, bindings CRUD generados por `wails_bind_crud_go_infra` |
|
|
|
|
---
|
|
|
|
### Pipeline 4: `init_cli_app`
|
|
|
|
Scaffold de Go CLI app con subcomandos y componentes TUI de Bubbletea.
|
|
|
|
**Uso:**
|
|
|
|
```bash
|
|
fn run init_cli_app my_cli
|
|
fn run init_cli_app my_cli --with-tui
|
|
```
|
|
|
|
**Archivos generados:**
|
|
|
|
```
|
|
apps/{nombre}/
|
|
├── main.go — Entry point con subcommand routing (os.Args)
|
|
├── cmd_version.go — Subcomando: version
|
|
├── cmd_status.go — Subcomando de ejemplo: status (imprime info)
|
|
├── app.md — framework vacio (CLI puro) o bubbletea (con --with-tui)
|
|
├── Makefile — Targets: build, run, install, test, clean
|
|
├── .gitignore
|
|
└── go.mod
|
|
```
|
|
|
|
**Con `--with-tui`:**
|
|
|
|
```
|
|
apps/{nombre}/
|
|
├── main.go — Entry point con run_fullscreen o run_model
|
|
├── model.go — BaseModel + Update + View con tema oscuro
|
|
├── cmd_version.go — Subcomando no-TUI
|
|
├── app.md — framework: bubbletea
|
|
├── Makefile
|
|
├── .gitignore
|
|
└── go.mod
|
|
```
|
|
|
|
**Funciones del registry compuestas:**
|
|
|
|
| Funcion | Para que |
|
|
|---------|---------|
|
|
| `assert_command_exists_bash_shell` | Verificar Go |
|
|
| `new_base_model_go_tui` | Modelo base en model.go |
|
|
| `dark_styles_go_tui` | Tema oscuro por defecto |
|
|
| `run_fullscreen_go_tui` | Arranque fullscreen en main.go |
|
|
| `new_spinner_go_tui` | Componente de ejemplo |
|
|
| `new_filtered_list_go_tui` | Componente de ejemplo |
|
|
|
|
**main.go generado (sin TUI):**
|
|
|
|
```go
|
|
package main
|
|
|
|
import (
|
|
"fmt"
|
|
"os"
|
|
)
|
|
|
|
var version = "dev"
|
|
|
|
func main() {
|
|
if len(os.Args) < 2 {
|
|
printUsage()
|
|
os.Exit(1)
|
|
}
|
|
|
|
switch os.Args[1] {
|
|
case "version":
|
|
cmdVersion()
|
|
case "status":
|
|
cmdStatus()
|
|
default:
|
|
fmt.Fprintf(os.Stderr, "unknown command: %s\n", os.Args[1])
|
|
printUsage()
|
|
os.Exit(1)
|
|
}
|
|
}
|
|
|
|
func printUsage() {
|
|
fmt.Println("Usage: {nombre} <command>")
|
|
fmt.Println()
|
|
fmt.Println("Commands:")
|
|
fmt.Println(" version Print version")
|
|
fmt.Println(" status Show status")
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
## Tareas
|
|
|
|
### Fase 1: `init_api_app` (pipeline base)
|
|
|
|
- [ ] **1.1** Crear `bash/functions/pipelines/init_api_app.sh` con source de funciones atomicas, parseo de argumentos, y generacion de estructura
|
|
- [ ] **1.2** Escribir heredocs para `main.go`, `handlers.go`, `config.go` que importen funciones de 0009 y 0015
|
|
- [ ] **1.3** Generar `app.md` con frontmatter correcto (tag `service`, `uses_functions` con IDs reales, `dir_path`)
|
|
- [ ] **1.4** Generar `Makefile`, `.env.example`, `.gitignore`, `migrations/001_initial.sql`
|
|
- [ ] **1.5** Flag `--with-auth`: anadir imports de 0010, handlers de login/register, tabla users en migration
|
|
- [ ] **1.6** Flag `--with-db`: anadir `store.go` con helpers CRUD, setup de SQLite al arrancar
|
|
- [ ] **1.7** Ejecutar `go vet -tags fts5` al final como verificacion
|
|
- [ ] **1.8** Crear `init_api_app.md` con frontmatter de pipeline
|
|
|
|
### Fase 2: `init_web_app` (extiende init_api_app)
|
|
|
|
- [ ] **2.1** Crear `bash/functions/pipelines/init_web_app.sh` que primero invoca la logica de `init_api_app` y luego anade el frontend
|
|
- [ ] **2.2** Generar `frontend/` con `package.json` (pnpm, vite, react, mantine, @fn_library alias)
|
|
- [ ] **2.3** Generar `vite.config.ts` con proxy al backend y alias `@fn_library`
|
|
- [ ] **2.4** Generar `src/main.tsx` con `FnMantineProvider`, `src/App.tsx` con `AppShell`, `src/pages/Home.tsx` con ejemplo
|
|
- [ ] **2.5** Generar `docker-compose.yml` para desarrollo
|
|
- [ ] **2.6** Actualizar `main.go` para servir static files del frontend build
|
|
- [ ] **2.7** Ejecutar `pnpm install && pnpm build` como verificacion del frontend
|
|
- [ ] **2.8** Crear `init_web_app.md` con frontmatter de pipeline
|
|
|
|
### Fase 3: `init_desktop_app`
|
|
|
|
- [ ] **3.1** Crear `bash/functions/pipelines/init_desktop_app.sh` que invoca `scaffold_wails_app_go_infra` y anade frontend React
|
|
- [ ] **3.2** Verificar/instalar Wails con `install_wails_bash_infra`
|
|
- [ ] **3.3** Generar frontend con `WailsProvider` + `FnMantineProvider` y ejemplo con `useWailsQuery`
|
|
- [ ] **3.4** Flag `--with-db`: invocar `wails_bind_crud_go_infra` para generar bindings
|
|
- [ ] **3.5** Ejecutar `wails build` como verificacion
|
|
- [ ] **3.6** Crear `init_desktop_app.md` con frontmatter de pipeline
|
|
|
|
### Fase 4: `init_cli_app`
|
|
|
|
- [ ] **4.1** Crear `bash/functions/pipelines/init_cli_app.sh` con generacion de estructura CLI basica
|
|
- [ ] **4.2** Generar `main.go` con routing de subcomandos, `cmd_version.go`, `cmd_status.go`
|
|
- [ ] **4.3** Flag `--with-tui`: generar `model.go` con `new_base_model`, `dark_styles`, `run_fullscreen`
|
|
- [ ] **4.4** Ejecutar `go vet` como verificacion
|
|
- [ ] **4.5** Crear `init_cli_app.md` con frontmatter de pipeline
|
|
|
|
### Fase 5: Integracion
|
|
|
|
- [ ] **5.1** `fn index` y verificar que los 4 pipelines aparecen en registry.db con kind=pipeline, purity=impure
|
|
- [ ] **5.2** Verificar `fn run init_api_app test_app` end-to-end: genera, compila, limpia
|
|
- [ ] **5.3** Verificar `fn run init_web_app test_web` end-to-end
|
|
- [ ] **5.4** Verificar `fn run init_desktop_app test_desktop` end-to-end
|
|
- [ ] **5.5** Verificar `fn run init_cli_app test_cli` end-to-end
|
|
|
|
### Fase 6: Documentacion de uso rapido
|
|
|
|
Cada pipeline debe ser usable sin leer el issue completo. La documentacion va en dos niveles: el `.md` de cada funcion (fuente de verdad para `fn show`) y una guia consolidada.
|
|
|
|
- [ ] **6.1** En cada `.md` de pipeline (`init_api_app.md`, etc.) documentar en la seccion `documentation` del frontmatter:
|
|
- Sinopsis: `fn run init_api_app <nombre> [--port N] [--with-auth] [--with-db]`
|
|
- Descripcion de cada flag y su efecto concreto (que archivos anade, que imports genera)
|
|
- Listado de archivos generados con una linea de descripcion cada uno
|
|
- Post-setup: que comandos ejecutar despues (`make run`, `make dev`, `wails dev`, etc.)
|
|
- Ejemplo rapido: un bloque copy-paste de 3-4 lineas que crea la app y la arranca
|
|
- [ ] **6.2** En el campo `params` del frontmatter de cada pipeline, documentar cada argumento y flag con `name` y `desc` semantico para que `fn check params` pase y la info sea buscable via FTS5
|
|
- [ ] **6.3** En el campo `example` del frontmatter, poner el caso de uso mas comun (una linea):
|
|
- `init_api_app`: `fn run init_api_app my_service --with-db`
|
|
- `init_web_app`: `fn run init_web_app my_dashboard --with-auth`
|
|
- `init_desktop_app`: `fn run init_desktop_app my_tool`
|
|
- `init_cli_app`: `fn run init_cli_app my_cli --with-tui`
|
|
- [ ] **6.4** Crear `docs/init-pipelines.md` como guia consolidada de referencia rapida con:
|
|
- Tabla resumen de los 4 pipelines (nombre, que genera, flags disponibles)
|
|
- Arbol de decision: "quiero una API" → init_api_app, "quiero frontend" → init_web_app, "quiero desktop" → init_desktop_app, "quiero CLI" → init_cli_app
|
|
- Seccion de combinaciones comunes (API + auth + DB, web dashboard, desktop con SQLite, CLI con TUI)
|
|
- FAQ: como anadir auth despues, como cambiar el puerto, como anadir operations.db, como agregar mas paginas al frontend
|
|
- [ ] **6.5** Verificar que `fn show init_api_app_bash_pipelines` (y los otros 3) muestra la documentacion completa con params, ejemplo y notas de uso
|
|
|
|
---
|
|
|
|
## Ejemplo de uso
|
|
|
|
```bash
|
|
# API service con auth y database
|
|
fn run init_api_app billing_api --port 8090 --with-auth --with-db
|
|
cd apps/billing_api
|
|
make run
|
|
# → starting billing_api on :8090
|
|
# → curl localhost:8090/health → {"status":"ok"}
|
|
|
|
# Full-stack dashboard
|
|
fn run init_web_app inventory_dashboard --with-auth
|
|
cd apps/inventory_dashboard
|
|
make dev
|
|
# → API en :8080, frontend en :5173 con proxy
|
|
|
|
# Desktop app con base de datos
|
|
fn run init_desktop_app data_explorer --with-db
|
|
cd apps/data_explorer
|
|
wails dev
|
|
# → App de escritorio con React + SQLite
|
|
|
|
# CLI con TUI
|
|
fn run init_cli_app deploy_helper --with-tui
|
|
cd apps/deploy_helper
|
|
make run -- status
|
|
# → TUI fullscreen con lista filtrable
|
|
```
|
|
|
|
**Cada pipeline genera su `app.md` listo para `fn index`:**
|
|
|
|
```yaml
|
|
---
|
|
name: billing_api
|
|
lang: go
|
|
domain: tools
|
|
description: "API de facturacion."
|
|
tags: [service]
|
|
uses_functions:
|
|
- http_serve_go_infra
|
|
- http_router_go_infra
|
|
- http_middleware_chain_go_infra
|
|
- http_cors_middleware_go_infra
|
|
- http_logger_middleware_go_infra
|
|
- http_json_response_go_infra
|
|
- http_error_response_go_infra
|
|
- migration_up_go_infra
|
|
uses_types: []
|
|
framework: "net/http"
|
|
entry_point: "main.go"
|
|
dir_path: "apps/billing_api"
|
|
---
|
|
```
|
|
|
|
---
|
|
|
|
## Decisiones de diseno
|
|
|
|
- **Bash, no Go:** los init pipelines generan archivos con heredocs — bash es el lenguaje natural para esto. Go seria overengineering para scaffolding de texto. Coherente con `init_jupyter_analysis` y los demas init existentes.
|
|
- **Composicion sobre monolito:** cada pipeline sourcea funciones atomicas del registry (`assert_command_exists`, `scaffold_wails_app`, etc.) en vez de reimplementar. Si una funcion atomica mejora, todos los pipelines se benefician.
|
|
- **init_web_app extiende init_api_app:** el pipeline web reutiliza la logica del API (misma estructura backend) y anade la capa frontend encima. No duplica codigo.
|
|
- **Verificacion al final:** cada pipeline termina con `go vet`, `pnpm build`, o `wails build` para garantizar que el scaffold compila. Si falla, el pipeline reporta el error antes de declarar exito.
|
|
- **Flags opcionales con defaults sensatos:** el caso base (sin flags) genera una app funcional minima. `--with-auth`, `--with-db`, `--with-tui` anaden capas incrementales. El usuario no necesita decidir todo upfront.
|
|
- **@fn_library como alias, no copia:** el frontend generado referencia `@fn_library` via alias en `vite.config.ts` apuntando a `frontend/functions/ui/` del registry. Los componentes se comparten, no se duplican.
|
|
- **app.md generado automaticamente:** el frontmatter incluye `uses_functions` con los IDs reales de las funciones que el boilerplate importa. `fn index` los valida al registrar la app.
|
|
- **Sin framework CLI externo para init_cli_app:** routing de subcomandos con `os.Args` y switch — consistente con las apps existentes del registry que no usan cobra/urfave. Para TUI se usa Bubbletea que ya esta en el registry.
|
|
|
|
## Riesgos
|
|
|
|
- **Dependencias no implementadas:** los tres issues de dependencia (0009, 0010, 0015) estan pendientes. Si alguna funcion cambia de firma durante su implementacion, los heredocs de los pipelines necesitaran ajuste. **Mitigacion:** implementar los pipelines despues de que las dependencias esten merged, o mantener los heredocs parametricos para absorber cambios menores.
|
|
- **Heredocs fragiles:** generar Go/TS/YAML con heredocs bash es propenso a errores de indentacion, escape de variables y quoting. **Mitigacion:** cada pipeline incluye verificacion final (`go vet` / `pnpm build`) que detecta errores de sintaxis inmediatamente. Tests end-to-end en fase 5.
|
|
- **Frontend desactualizado respecto a @fn_library:** si los componentes de `frontend/functions/ui/` evolucionan, el boilerplate generado puede quedar desactualizado. **Mitigacion:** el boilerplate es minimo (un Provider, un AppShell, una pagina de ejemplo) — el usuario lo extiende con los componentes actuales del registry.
|
|
- **Wails como dependencia de sistema:** `init_desktop_app` requiere GTK3 + WebKit2GTK instalados en Linux. `install_wails_bash_infra` lo maneja, pero puede fallar en distros no soportadas. **Mitigacion:** el pipeline verifica la instalacion al inicio y falla rapido con mensaje descriptivo.
|
|
- **Colision de nombres:** si el usuario elige un nombre que ya existe en `apps/`, el pipeline sobreescribiria archivos. **Mitigacion:** verificar si `apps/{nombre}/` existe al inicio y abortar con error si ya existe.
|