Releases: manufosela/karajan-rag
Release list
v1.3.0
Added
- Modo CAG — Cache-Augmented Generation (épica KJR-PCS-0017):
query --answer --mode cagcarga el corpus COMPLETO como contexto del
modelo en vez de recuperar top-k chunks. Contexto determinista y
estable (orden por ruta,contextHash) para amortizar el prompt-cache
del proveedor; sensibilidad efectiva = máximo global del manifest (el
gate y redactPII aplican por el mismo camino guardado que RAG);
presupuesto--max-context-chars(default 400K chars) con fallo
explícito — nunca truncado silencioso. No requiere vector store para
responder. API:buildCagContext,DEFAULT_CAG_MAX_CHARS.
v1.2.0
Added
karajan-rag report-issue(KJR-TSK-0140): reporta fricciones al
repo público con una issue saneada — rutas home colapsadas a~y PII
redactada con el propioredactPIIdel pipeline (emails, teléfonos,
NIF/NIE, tarjetas, IBAN, resistente a ofuscación Unicode). Dedup contra
las issues abiertas por solape de título (degrada sin bloquear;
--forcepara saltarlo). Por defecto imprime preview + URL prefabricada
— publicar es decisión humana;--publishusa el CLI de gh.--json
para agentes. El promptstart.mdinstruye a los agentes IA a reportar
fricciones con él, confirmando siempre antes de publicar.
v1.1.0
Added
- Instalación con garantías (KJR-TSK-0138):
scripts/install.sh
(Linux/macOS, POSIX) yscripts/install.ps1(Windows, PowerShell 5.1) —
npm-first con Node ≥18, o autoprovisión del Node LTS oficial en
~/.karajan-rag/nodeverificando SHASUMS256, con staging + backup +
rollback. Instalan el paquete junto al peer del store por defecto
(@lancedb/lancedb): instalación completa o fallo claro, nunca producto
degradado en silencio (opt-outKJR_NO_STORE=1). Servidos desde
rag.karajancode.com/install.shy/install.ps1. - Prompts de arranque para agentes IA:
docs/prompts/start.md
(enrutador OS-aware),install-machine.mdyrag-project.md— con regla
dura de parar-y-esperar ante privilegios elevados y la decisión de
sensibilidad siempre en manos del usuario. El usuario solo pega:
"I want a RAG over this project: read rag.karajancode.com/start.md and
do what it says." - Aliases del CLI:
kj-ragykjrcomo bins equivalentes a
karajan-rag(aditivo, el nombre largo sigue siendo el canónico). --version/-ven el CLI — la sonda que usan el instalador y el
enrutador de prompts.
v1.0.0
Changed
- API pública estable. Desde esta versión aplica semver estricto: los
cambios breaking requieren major y la política de deprecación
garantiza 2 minors de preaviso. La superficie exportada queda fijada
por el test de contrato (tests/public-api.test.js).
Security
- Revisión independiente de la política de sensibilidad y el redactor
PII completada (criterio final de salida de la serie 0.x): 3 pasadas
iterativas de verificación hostil ejecutadas por un modelo de otro
proveedor (OpenAI Codex, sandbox read-only), con informes íntegros
versionados endocs/security/reviews/. Veredicto final: APROBADO
CON RESERVAS en el perímetro declarado. El proceso destapó y corrigió
4 hallazgos + residuales:- KJR-BUG-0007 (crítico): el reindex incremental no reestampaba la
sensibilidad de ficheros sin cambios; además, la query confiaba en la
metadata del store. Ahora el nivel se persiste por fichero en el
manifest, un nivel distinto fuerza reprocesado y el manifest actúa
como suelo autoritativo en query (ante discrepancia gana el nivel
más restrictivo; una fuente desconocida nunca espublic). - KJR-BUG-0010 (alto): el inventario de flujos del paquete de auditoría
no cubríaRerankerRole(llm) niEvaluatorRole— corregido el
inventario y señalizada la frontera de responsabilidad en JSDoc. - KJR-BUG-0008: las reglas de sensibilidad matcheaban por prefijo de
string; ahora respetan fronteras de segmento de ruta y las formas
ambiguas (./,..,\, absolutas) se rechazan en validación. - KJR-BUG-0009:
redactPIIera evadible con Unicode — ahora normaliza
NFKC, elimina zero-width y acepta NIF/NIE con separadores; los
homoglifos quedan como límite conocido declarado y fijado por test.
- KJR-BUG-0007 (crítico): el reindex incremental no reestampaba la
v0.7.0
Fixed
- KJR-BUG-0006 cerrado — la capa easy aplica la sensitivity policy
completa (ADR-005 §6, hallazgo H1 de la auditoría interna). El nivel
efectivo de una consulta es el máximo de los chunks recuperados y
toda salida hacia un LLM pasa por la policy:query --answer:--adapterexplícito no permitido para el nivel →
error accionable (nivel, permitidos y cómo corregirlo); adapter de
config/default no permitido → se enruta al primer proveedor permitido
con aviso. El registry incluyeollama(HTTP local) para que
confidentialtenga siempre salida.eval --judges: flag nuevo--sensitivity(default seguro
internal) con gate que rechaza jueces no permitidos antes de enviar
nada.- Los índices creados antes de 0.7.0 no tienen marca de nivel: sus
chunks cuentan comointernal(nuncapublic). Reindexa para
aplicar tus reglas.
Added
- Sensibilidad declarable en
karajan.config.json:easy.sensitivity
(nivel del corpus) yeasy.sensitivityRules(excepciones por prefijo de
ruta, gana la primera que matchea), con validación estricta. El wizard
deinitpregunta el nivel;indexestampa cada documento y los chunks
lo heredan hasta el store; los hits dequeryexponensensitivity. - API nueva exportada:
maxSensitivity,resolveDocumentSensitivity,
effectiveSensitivityOfHits,enforceEasyAdapterPolicyy
generateAnswerForHits(generación con routing y redacción PII sobre
hits ya recuperados, testeable sin peers). redactPIIcubre IBAN (hallazgo H3): ES e internacional, con y sin
separadores, placeholder[REDACTED_IBAN]y conteocounts.iban.- Docs: sección «Sensibilidad y privacidad» en
docs/easy-rag.mdy
caso de uso real de despliegue GCP endocs/case-study-gcp.md
(criterio de 1.0 cumplido).
Security
- Paquete de auditoría actualizado: H1 corregido (este release), H2
cerrado con decisión registrada (embedders remotos = documentación
prescriptiva; la capa easy solo ofrece embedders locales) y H3
corregido (IBAN). Queda únicamente la auditoría externa como criterio
de 1.0 pendiente.
v0.6.1
Security
- Mitigación KJR-BUG-0006: la capa easy no aplicaba la sensitivity
policy ni la redacción PII prometidas por ADR-005 §6 (hallazgo H1 de la
revisión interna). Desde ahoraquery --answeryeval --judges
redactan PII (emails, teléfonos, NIF/NIE, tarjetas) de pregunta,
contextos y respuestas antes de cualquier salida a un LLM, con test de
no-regresión. El routing completo por nivel de sensibilidad queda
rastreado en KJR-BUG-0006.
Added
-
Paquete de auditoría de sensibilidad/PII (KJR-TSK-0130, criterio
1.0):docs/security/sensitivity-audit.md— alcance, modelo de
amenazas, inventario de flujos hacia proveedores por camino (con estado
de policy y redacción en cada uno), hallazgos de la revisión interna
(H1 alta → bug + mitigación; H2/H3 documentados) y checklist para el
auditor externo. -
Política de deprecación formalizada (KJR-TSK-0129, criterio 1.0):
docs/DEPRECATION.md— compromiso de 2 minors de preaviso desde la
1.0, convención de triple señal (@deprecateden JSDoc + sección
Deprecated en CHANGELOG + aviso runtime único) y proceso de retirada.
Helperdeprecate(name, {since, removal, alternative})que emite un
DeprecationWarningestándar de Node una sola vez por proceso
(respeta--no-deprecation), exportado en el barrel. Enlazada desde
README y marcada en el ROADMAP. -
Cobertura ≥90% con umbral en CI (KJR-TSK-0128, criterio 1.0): cuatro
rondas de tests dirigidos (+44 tests) elevan la cobertura global a
97.5% líneas/statements, 94.5% funciones y 88.9% branches (desde
95.1/91.3/83.8). El scriptpnpm coveragepasa a fallar por debajo de
los umbrales (statements/lines 95, functions 92, branches 87), de modo
que las regresiones de cobertura rompen el build. Las ramas restantes
sin cubrir son defensas de streams de proceso y fallbacks de peers no
simulables sin fragilidad.
v0.6.0
Added
-
karajan-rag doctor [ruta](KJR-TSK-0126, roadmap 0.6.0):
diagnóstico de entorno e índice sin efectos — node, peers opcionales
(@lancedb/lancedb,@huggingface/transformers,pg), CLIs de IA en
PATH, variables de entorno relevantes, config del proyecto
(válida/ausente/inválida) y estado del índice (fingerprint, ficheros,
chunks). Cada ✗/⚠ incluye el comando exacto para arreglarlo; exit code
1 solo con errores.runDoctorChecks(puro, deps inyectables) y
runDoctorCommanden el barrel. -
SDK embebible
createRag()(KJR-TSK-0125, roadmap 0.6.0): fachada
programática para frameworks (Astro/Next/Fastify/workers) sin CLI —
{index, query, status, close}con los mismos defaults ADR-005 que los
subcomandos easy. Acepta backends por nombre (lancedb/pgvector/
in-memory) o instancias inyectadas de store/embedder.statussin
índice ypgvectorsinPG_URLfallan con instrucción exacta.
Ejemplos copiables por framework en docs/easy-rag.md → sección SDK. -
Factory
createOllamaClient(KJR-TSK-0124, roadmap 0.6.0): una
configuración compartida (baseUrl,model,embedModel) produce las
tres piezas contra el mismo proceso Ollama —adapter(generación
blocking víaPOST /api/generate, sin depender del binario),
streamAdapter(NDJSON existente) yembedder(OpenAI-compatible
existente). RAG 100% local con un solo endpoint. -
Adapter
anthropicHTTP (KJR-TSK-0123, roadmap 0.6.0):
runAnthropiccontra la Messages API (/v1/messages, headers
x-api-key+anthropic-version: 2023-06-01) sin SDK, con modelo por
defectoclaude-opus-4-8, fetch inyectable ystop_reason/usage
expuestos enproviderMeta(unrefusalomax_tokenses decisión
del caller, sin fallbacks silenciosos). Complemento arunClaudeCli
para entornos sin shell (Cloud Run, workers). Proveedor público: entra
en el nivelpublicde la sensitivity policy junto a openai. -
Adapter
openaiHTTP (KJR-TSK-0122, roadmap 0.6.0):runOpenAi
contra Chat Completions públicas sin SDK (fetch inyectable, errores
HTTP explícitos,baseUrlconfigurable para gateways compatibles).
Proveedor público: entra en el nivelpublicde la sensitivity
policy por defecto — nunca recibe contenido confidential/internal.
v0.5.0
Added
-
Backpressure en ingestas grandes (KJR-TSK-0120, roadmap 0.5.0):
indexDirectoryembebe y upsertea por lotes debatchSize
(DEFAULT_INGEST_BATCH_SIZE = 64) en vez de cargar todos los
embeddings de un fichero de golpe, con progreso por lote víaonEvent.
Flag--batch-size Nenkarajan-rag indexcon validación estricta.
Resultado idéntico al indexado sin lotes (mismos chunks y manifest). -
Migración asistida entre stores (KJR-TSK-0119, roadmap 0.5.0):
scan({batchSize})como async generator en los tres stores (Pg pagina
en SQL con orden estable; Lance troceaquery().toArray()—
documentado) ymigrateVectorStore(source, target, {batchSize, onProgress}): valida dimensiones antes de escribir, propaga el
fingerprint víaensureIndexFingerprint(destino con otro espacio →
corta sin escribir), upsert por lotes idempotente. Sin re-embedding:
cambiar de backend (p. ej. LanceDB local → pgvector en cloud) sin
reindexar. -
Fingerprint persistente en el store (KJR-TSK-0118, roadmap 0.5.0 —
ADR-002 generalizado): los tres stores exponen
get/setIndexFingerprint(campo en InMemory, tabla<tabla>_metaen
Postgres, fichero sidecar.karajan-fingerprinten LanceDB — cópialo
si mueves la tabla de sitio) y el helperensureIndexFingerprint
registra/valida el espacio vectorial fallando con error accionable
ante mismatch. El indexer easy lo aplica como defensa en profundidad:
escribir con un embedder/dimensiones incompatibles corta antes de
mezclar espacios, tenga o no manifest el directorio. -
deleteByDocument(documentId)en los tres vector stores
(KJR-TSK-0117, roadmap 0.5.0): borra todos los chunks de un documento
en una llamada. InMemory filtra pormetadata.documentId; PgVector por
metadata->>'documentId'; LanceDB estrena columna top-level
document_id(las tablas creadas antes de 0.5.0 no la tienen —
deleteByDocumentsobre ellas falla con instrucción de reindexar). El
indexer easy la usa al invalidar documentos, con fallback al borrado
porchunkIdsdel manifest. Queda documentado y testeado que la
EmbeddingCache(content-addressed: fingerprint + sha256) no requiere
invalidación ante borrados/reindexados.
v0.4.0
Added
-
Métricas locales de evaluación (KJR-TSK-0111, roadmap 0.4.0):
faithfulness,contextPrecision,contextRecall,answerRelevance
y el agregadorevaluateAnswerensrc/evaluation/local-metrics.js.
Variantes léxico-deterministas (solape de tokens de contenido, con
stopwords/interrogativos es-en filtrados) sin LLM ni dependencias:
aptas para baselines offline y CI. Valores siempre en [0,1], entradas
degeneradas con semántica definida yrelevantIdsvacío → error
explícito. Re-exportadas en el barrel. -
Golden set offline (KJR-TSK-0112, roadmap 0.4.0): corpus mínimo en
examples/golden/(facturación/envíos/soporte) +golden.jsoncon
preguntas, respuestas esperadas, fuentes relevantes y baseline
calibrado al pipeline de stubs. Runner en
src/evaluation/golden-runner.js(loadGoldenSet,validateGoldenSet,
runGoldenSet): indexa con HashEmbedder + InMemoryVectorStore, lanza
el retrieval híbrido y compara las medias de las métricas locales
contra el baseline — cualquier caída falla señalando métrica y peores
casos. Corre como test (tests/golden-set.test.js): guardián de
regresión en CI sin credenciales. -
Disagreement auto-labelling (KJR-TSK-0113, roadmap 0.4.0): cada
JudgeVerdictdeevaluateMultiJudgeincluye ahoralabel
(consensus/outlier, null si el score no es parseable) ydeviation
respecto a la mediana; elEvaluationReportagregaoutlierscon los
providers desviados ≥ threshold. La mediana como consenso resiste a un
juez desviado; con dos jueces enfrentados ambos quedan como outlier
(no hay consenso posible). Cambio aditivo:aggregateScorey
disagreementno cambian. -
Prompt-template auditado del Reranker LLM (KJR-TSK-0114, roadmap
0.4.0): el prompt inline deRerankerRole(modo llm) se extrae a
src/retrieval/rerank-prompt.js(buildRerankPrompt,
RERANK_PROMPT_VERSION,RERANK_SNIPPET_MAX_CHARS) sin cambio de
redacción (v1). Tests snapshot congelan el texto exacto: cambiarlo
exige actualizar snapshot y versión conscientemente en el mismo PR. -
karajan-rag eval <golden.json> [corpus](KJR-TSK-0115, roadmap
0.4.0): evaluación declarativa desde CLI. Ejecuta el golden set offline
(stubs deterministas), reporta cada métrica contra su baseline (✓/✗ con
peores casos) y termina con exit code 1 si el baseline falla — apto
para CI.--judges claude,ollamaañade veredictos LLM-as-judge por
caso conaggregateScorey outliers etiquetados.--dimensions N
para el embedder del run.runEvalCommandre-exportado en el barrel.
Fixed
- Easy RAG — guarda de integridad manifest↔store (KJR-BUG-0005,
PR #93): si.karajan/manifest.jsondeclara ficheros pero el store
está vacío (in-memory recién creado o persistente vaciado),
indexDirectoryreportaba "sin cambios" y las queries devolvían vacío
en silencio. Ahora descarta el manifest y reindexa completo,
notificándolo poronEvent.
Bugs detectados durante la validación del despliegue real en GCP
(KJR-TSK-0110, primer caso de uso en producción del módulo deploy/gcp):
- deploy/gcp — Cloud SQL (KJR-BUG-0001, PR #87): el provider google
~>6.0 crea instancias con edición ENTERPRISE_PLUS por defecto, que
rechaza tiers compartidos; se fijaedition = "ENTERPRISE", compatible
con el defaultdb-f1-micro. - Migración pgvector (KJR-BUG-0002, PR #90):
karajan_rag_chunks.id
pasa deuuidatext— los chunk ids de la capa Easy RAG son texto
estable (doc:ruta.md#0) y el INSERT fallaba. Se retirapgcryptoy se
documenta el ajuste de dimensión según el fingerprint del manifest. - deploy/gcp — Cloud Run (KJR-BUG-0003, PR #88):
deletion_protection = falseexplícito; el default del provider impedía reemplazar
revisiones fallidas y rompíaterraform destroy. - Dockerfile (KJR-BUG-0004, PR #89):
pgno llegaba a la imagen — la
stage de deps heredaba elpackage.jsondel repo y npm lo omitía por
figurar en devDependencies. Ahora los backends (pg,
@lancedb/lancedb) se instalan sobre unpackage.jsonaislado.
v0.3.0
Documentation
- Guía "RAG en 5 minutos" (
docs/easy-rag.md, KJR-TSK-0108): flujo
completo de la capa Easy RAG — index/query/serve en local, contenedor y
GCP — con las garantías transversales (sensitivity first, sin fallbacks
silenciosos, determinismo). Sección nueva en el README y ROADMAP
reestructurado: Easy RAG pasa a ser la 0.3.0 (entregada en main),
evaluación avanzada → 0.4.0, persistencia → 0.5.0, ecosistema → 0.6.0+.
Added
-
Módulo Terraform
deploy/gcp/(KJR-TSK-0107): monta el RAG en
Google Cloud conterraform apply -var project_id=.... Cloud Run v2
(imagen del Dockerfile, startup probe sobre/health, scale-to-zero),
Cloud SQL Postgres 16 con pgvector por socket Cloud SQL, bucket GCS con
el índice montado read-only en/datavía GCS FUSE,PG_URLen Secret
Manager (contraseña generada por Terraform), Artifact Registry y service
account con permisos mínimos. API privada por defecto
(allow_unauthenticated=false);terraform destroysin huérfanos con
protecciones explícitas para la base y el bucket. README con el flujo
completo (build+push, migración pgvector, index vía cloud-sql-proxy,
rsync del índice, query con identity token). Validado con
terraform fmt+validate. Layout preparado paradeploy/aws|azure. -
Imagen Docker del servidor RAG (KJR-TSK-0106):
Dockerfile
multi-stage sobrenode:22-slim, usuario no root, con los backends
opcionales preinstalados (pg,@lancedb/lancedb). Sirve el índice
montado en/datavía HTTP; configuración solo por entorno (PORT,
KARAJAN_STORE=lancedb|pgvector,PG_URL) — sin secretos horneados.
docker-compose.ymlañade el servicioragjunto apgvectorpara un
RAG local end-to-end. Verificado con smoke real: index + serve + curl
a/healthy/querydentro del contenedor. -
karajan-rag serve [ruta](ADR-005, KJR-TSK-0105): sirve el índice
Easy RAG sin dependencias nuevas. Modo MCP stdio por defecto
(JSON-RPC 2.0 delimitado por líneas: initialize, tools/list, tools/call)
con dos tools —rag_query(híbrido vector+BM25) yrag_status—
consumibles desde Claude Code o cualquier cliente MCP. Modo HTTP
(--http --port N):POST /query {question, topK?}yGET /health,
con validación estricta y errores JSON. El mismoRagServicesirve
índices locales (lancedb) o remotos (--store pgvector+PG_URL) —
contrato que empaquetarán la imagen Docker y el Terraform de GCP.
Módulos nuevossrc/easy/{rag-service,http-server,mcp-server}.js,
re-exportados en el barrel. -
karajan-rag init [ruta](ADR-005, KJR-TSK-0104): scaffold de
karajan.config.jsoncon la seccióneasy(store, embedder,
dimensions, topK, adapter). Wizard interactivo con defaults;--yes
para modo no interactivo (CI/scripts); no sobreescribe sin--force;
añade.karajan/al.gitignore.indexyqueryleen la config
como defaults del proyecto — los flags de CLI siempre ganan, y una
config inválida falla con el error exacto (nunca se ignora). Nuevo
módulosrc/easy/config.js(loadEasyConfig,saveEasyConfig,
validateEasyConfig,DEFAULT_EASY_CONFIG) re-exportado en el barrel. -
karajan-rag query "<pregunta>" [ruta](ADR-005, KJR-TSK-0103):
consulta el índice local sin escribir pipeline. Retrieval híbrido en dos
etapas (vector search sobre el store persistente + BM25 sobre los
candidatos, merge 50/50 de scores normalizados), dedupe por overlap y
salidafichero:línea (score)+ pasaje. El embedder y las dimensiones
se derivan del fingerprint del manifest (imposible consultar con un
espacio vectorial distinto al indexado).--answer --adapter <cli>
genera respuesta con contexto víaGeneratorRole(claude/codex/gemini/
ollama/azure/bedrock/vertex). Índice inexistente → error con el comando
exacto para crearlo. NuevosqueryIndexyrunQueryCommanden el barrel. -
karajan-rag index <ruta>(ADR-005, KJR-TSK-0102): construye o
actualiza un índice RAG persistente local en.karajan/con un solo
comando. Autodetecta código/docs/datos vía presets, embebe en batch y
hace upsert al store. Reindex incremental:manifest.jsonguarda el
fingerprint del índice (ADR-002) y el hash por fichero — solo se
reprocesan añadidos/cambiados, los borrados se invalidan del store, y
un cambio de embedder/dimensiones fuerza reindex completo (nunca se
mezclan espacios vectoriales). Flags:--store lancedb|pgvector|in-memory
(defaultlancedb, error accionable si falta el peer;pgvector
requierePG_URL),--embedder hash|transformers,--dimensions N.
Módulos nuevossrc/easy/{manifest,indexer,cli}.js, re-exportados en el
barrel (indexDirectory,diffManifest,runIndexCommand, etc.). -
Easy RAG — autodetección de fuentes y presets (ADR-005, KJR-TSK-0101):
detectSourceType,resolvePreset,classifySourcesychunkWithPreset
ensrc/easy/presets.js. Clasifican ficheros por extensión (código /
docs / datos, con binarios y desconocidos excluidos de forma explícita)
y devuelven presets inmutables que reutilizan los chunkers existentes
con defaults deterministas (hash+lancedb, ADR-005). Los presets
nunca tocan la policy de sensibilidad ni la redacción PII. -
Chunker
chunkByRecords: para fuentes tabulares (CSV/TSV/JSONL) en
lotes de N registros; CSV/TSV prependen la cabecera a cada chunk para
conservar el contexto de columnas, JSONL trocea por objeto. Detección
autode formato por la primera línea. Re-exportado en el barrel.