Worker de ingestión de analytics opcional para self-hosted Enterprise. Alimenta los dashboards del Cockpit (DORA, ciclo de vida, classifier).
El analytics worker es un add-on exclusivo de Enterprise. Ejecuta el
cron de ingestión que alimenta los dashboards del Cockpit (métricas tipo
DORA, ciclo de vida de PR, classifier de PR basado en LLM).
El instalador por defecto no incluye este worker. Los despliegues
self-hosted de la versión community no lo necesitan y estas vars se
filtran del .env.example por defecto. Detente aquí a menos que tengas
una licencia self-hosted Enterprise y quieras los reportes del Cockpit.
Un proceso Node separado ejecutando la misma imagen del worker
(kodus-ai-worker), seleccionado en el boot vía WORKER_ROLE=analytics.
Dos crons disparan desde este proceso y solo desde él:
Ingestión (ANALYTICS_INGESTION_CRON, default */30 * * * *) — lee
pull requests y sesiones de review desde Mongo + el Postgres OLTP, y los
proyecta al schema analytics.
Classifier (ANALYTICS_CLASSIFIER_CRON, default */15 * * * *) —
llama un LLM para etiquetar cada PR con un tipo (feature/bugfix/refactor/etc).
Aislarlo del worker principal mantiene el event loop de code review
libre de queries de ingestión largas.
El warehouse de analytics es un schema de Postgres, no una base de
datos separada. Dos layouts soportados:
Postgres compartido (recomendado para self-hosted) — deja
ANALYTICS_PG_DB_HOST vacío. El config loader cae en el fallback de
las vars API_PG_DB_* y crea un schema analytics en la misma
instancia. Una sola DB para respaldar y operar.
Postgres dedicado — define el bloque ANALYTICS_PG_DB_* apuntando
a otra instancia. Úsalo cuando quieras queries analíticas totalmente
aisladas del write path del OLTP.
El contenedor worker-analytics comparte el mismo prod-entrypoint.sh
que api/worker/webhooks. Con RUN_MIGRATIONS=true (default del
installer), las migrations del warehouse de analytics
(pnpm run analytics:migration:run:prod) corren en el primer boot, creando
el schema analytics y sus tablas.
Para detener la ingestión en runtime sin remover el contenedor, define
ANALYTICS_INGESTION_DISABLED=true y/o ANALYTICS_CLASSIFIER_DISABLED=true
y reinicia worker-analytics. El cron sigue agendado pero cada tick
hace short-circuit. Úsalo para triaje de incidentes, no como config a
largo plazo — esas vars se gestionan principalmente para cloud y pueden
no aparecer en el template del installer.
Después del boot, sigue los logs del analytics worker:
docker compose logs -f worker-analytics
Debes ver líneas como analytics ingestion done in NNNms — {...} cada
30 minutos y analytics classifier done ... cada 15 minutos. Si no,
confirma que WORKER_ROLE=analytics está seteado solo en este
contenedor (no en el worker principal — ese debe permanecer en
code-review).
{"docsConfig":{"theme":"aspen","$schema":"https://mintlify.com/docs.json","name":"Kodus","colors":{"primary":"#F8B76D","light":"#F8B76D","dark":"#443024"},"logo":{"light":"https://mintcdn.com/kodus/AF97E4sqQ0bDm2vv/logo/light.svg?fit=max\u0026auto=format\u0026n=AF97E4sqQ0bDm2vv\u0026q=85\u0026s=f936e2273166bb149af32c25f012a088","dark":"https://mintcdn.com/kodus/AF97E4sqQ0bDm2vv/logo/dark.svg?fit=max\u0026auto=format\u0026n=AF97E4sqQ0bDm2vv\u0026q=85\u0026s=25fb99797bf5f026442124edd13ca06c","href":"https://kodus.io"},"favicon":"https://mintcdn.com/kodus/AF97E4sqQ0bDm2vv/favicon.svg?fit=max\u0026auto=format\u0026n=AF97E4sqQ0bDm2vv\u0026q=85\u0026s=20fa3480d131c22d3c2f971dec149d41","background":{"color":{"dark":"#101019"}},"navbar":{"links":[{"href":"https://discord.gg/TFZBRk9fT6","label":"Community"},{"href":"https://github.com/kodustech","label":"Github"}],"primary":{"type":"button","label":"Try Kodus","href":"https://kodus.io/"}},"footer":{"socials":{"twitter":"https://twitter.com/kodustech","github":"https://github.com/kodustech","linkedin":"https://www.linkedin.com/company/kodustech"}},"integrations":{"gtm":{"tagId":"GTM-5MWMVQDC"},"posthog":{"apiKey":"phc_eXdASBHYhvHzYCLktmceTdRKmF3jMLnrH4iCXXUGjJI"}},"contextual":{"options":["copy","view","chatgpt","claude"],"display":"header"},"styling":{"latex":true},"navigation":{"languages":[{"language":"en","href":"en/how_to_use/overview"},{"language":"es","href":"es/how_to_use/overview"},{"language":"pt-BR","href":"pt-BR/how_to_use/overview"},{"language":"ja","href":"ja/how_to_use/overview"},{"language":"zh","href":"zh/how_to_use/overview"}]}},"deployment":{"deploymentMetadataValue":{"subdomain":"kodus","hasAudioNarration":false,"actualSubdomain":"kodus","customDomains":["docs.kodus.io"],"gitSource":{"type":"github","owner":"kodustech","repo":"kodus-ai","deployBranch":"main","contentDirectory":"docs","isPrivate":false,"mountPath":"","label":""},"chroma":{"liveDeploymentHistoryId":"6aebbaf91919761fe16dbc20","collectionId":"a1740fe2-55dc-4398-a1bf-fbbf11cb6e28","schemaVersion":"v3","latestBuiltDeploymentHistoryId":"6aebbaf91919761fe16dbc20"},"feedback":{"thumbs":true,"edits":true,"issues":true},"entitlements":{},"buildId":"6aebbaf91919761fe16dbc20","clientVersion":"0.0.4067","searchFilterCounts":[{"language":"en","tag":"How to use","count":60},{"language":"es","tag":"Cómo usar","count":60},{"language":"ja","tag":"使い方","count":60},{"language":"pt-BR","tag":"Como usar","count":60},{"language":"zh","tag":"如何使用","count":60},{"language":"en","tag":"Knowledge Base","count":26},{"language":"es","tag":"Base de Conocimiento","count":26},{"language":"ja","tag":"ナレッジベース","count":26},{"language":"pt-BR","tag":"Base de Conhecimento","count":26},{"language":"zh","tag":"知识库","count":26},{"language":"en","tag":"AI Code Review","count":25},{"language":"es","tag":"Revisión de Código con IA","count":25},{"language":"ja","tag":"AIコードレビュー","count":25},{"language":"pt-BR","tag":"Revisão de Código com IA","count":25},{"language":"zh","tag":"AI 代码审查","count":25},{"language":"en","tag":"How to deploy","count":19},{"language":"es","tag":"Cómo desplegar","count":19},{"language":"ja","tag":"デプロイ方法","count":19},{"language":"pt-BR","tag":"Como implantar","count":19},{"language":"zh","tag":"如何部署","count":19},{"language":"en","tag":"Cookbook","count":18},{"language":"es","tag":"Recetario","count":18},{"language":"ja","tag":"クックブック","count":18},{"language":"pt-BR","tag":"Cookbook","count":18},{"language":"zh","tag":"食谱","count":18},{"language":"en","tag":"Cockpit","count":12},{"language":"es","tag":"Cockpit","count":12},{"language":"ja","tag":"コックピット","count":12},{"language":"pt-BR","tag":"Cockpit","count":12},{"language":"zh","tag":"驾驶舱","count":12},{"language":"en","tag":"Advanced Configs","count":10},{"language":"es","tag":"Configuraciones Avanzadas","count":10},{"language":"ja","tag":"詳細設定","count":10},{"language":"pt-BR","tag":"Configurações Avançadas","count":10},{"language":"zh","tag":"高级配置","count":10},{"language":"en","tag":"Metrics","count":9},{"language":"es","tag":"Métricas","count":9},{"language":"ja","tag":"メトリクス","count":9},{"language":"pt-BR","tag":"Métricas","count":9},{"language":"zh","tag":"指标","count":9},{"language":"en","tag":"LLM Provider Setup","count":8},{"language":"en","tag":"Deploy with Docker","count":8},{"language":"es","tag":"Configuración de Proveedor LLM","count":8},{"language":"es","tag":"Despliegue con Docker","count":8},{"language":"ja","tag":"LLM プロバイダー設定","count":8},{"language":"ja","tag":"Dockerでデプロイ","count":8},{"language":"pt-BR","tag":"Configuração de Provedor LLM","count":8},{"language":"pt-BR","tag":"Implantar com Docker","count":8},{"language":"zh","tag":"LLM 提供商配置","count":8},{"language":"zh","tag":"使用 Docker 部署","count":8},{"language":"default","tag":"Changelog","count":1}]},"assistantConfig":{},"basePath":"","hasChatPermissions":false,"hasWebMcpPermissions":false,"toggles":[{"name":"kill-isr","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"agent-mintlify-slack","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"agent-integrations-settings","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"rbac-expansion","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"automations-pr-grouping","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"custom-prefix","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"analytics-v7","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"user-flows-analytics","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"no-publish-flow","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"workos-onboarding","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"llms-txt-v2","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"snapshot-serving-live","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"stripTemperatureMiddleware","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"support-platform-pylon-zendesk","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"snapshot-serving","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"instant-rollback","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"granular-notifications-server","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"granular-notifications","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"automations-fable","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"fixed-ai-action-pricing","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"automation-resolve-merge-conflict","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"scoped-publishing","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"mintql","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"page-level-analytics","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"editor-version-history-v2","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"billing-page-v2","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"full-page-search","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"workspace-projects","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"assistant-v5","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"fork-pr-previews","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"revalidation-jwt","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"vite-origin","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"workos-sso-scim","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"hobby-abuse-scan","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"dashboard-inbox","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"workos-signup","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"turbopuffer-dual-write","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"workos-enabled","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"approve-review-flow","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"sso-setup-deadline-banner","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"turbopuffer-serve","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false}],"googleFontsInlined":false},"customCss":[{"filePath":"style.css","content":"#content-area:has(.kodus-changelog-release) #header .eyebrow{display:none}body:has(.kodus-changelog-release) div.ml-4.flex.text-sm.leading-6.whitespace-nowrap.min-w-0.space-x-3.overflow-hidden{display:none}body:has(.kodus-changelog-release) #content-side-layout,body:has(.kodus-changelog-release) #table-of-contents-layout,body:has(.kodus-changelog-release) #table-of-contents{display:none!important}body:has(.kodus-changelog-release) #content-container{max-width:none!important;padding-right:24rem!important}body:has(.kodus-changelog-release) #content-area{width:100%!important;max-width:54rem!important;margin-right:auto!important;margin-left:0!important}body:has(.kodus-changelog-release) header a[href*=\"changelog\"]{position:relative;color:#faf8f6!important}body:has(.kodus-changelog-release) header a[href*=\"changelog\"] *,body:has(.kodus-changelog-release) header a[href*=\"changelog\"] svg{color:#faf8f6!important;stroke:currentColor}body:has(.kodus-changelog-release) header a[href*=\"changelog\"]::after{content:\"\";position:absolute;right:0;bottom:-1px;left:0;height:2px;background:#f8b76d}body:has(.kodus-changelog-release) header a[href*=\"changelog\"]:hover,header a[href*=\"changelog\"]:hover{color:#f8b76d!important}body:has(.kodus-changelog-release) header a[href*=\"changelog\"]:hover *,body:has(.kodus-changelog-release) header a[href*=\"changelog\"]:hover svg,header a[href*=\"changelog\"]:hover *,header a[href*=\"changelog\"]:hover svg{color:#f8b76d!important;stroke:currentColor}.kodus-changelog-release{display:grid;grid-template-columns:minmax(6.5rem, 8rem) minmax(0, 36rem);column-gap:1.75rem;align-items:start;margin-top:2.5rem;padding-top:2rem;border-top:1px solid rgba(248, 183, 109, 0.18)}.kodus-changelog-release[hidden]{display:none!important}.kodus-changelog-meta{position:sticky;top:8.5rem;align-self:start;display:flex;flex-direction:column;align-items:flex-start;gap:0.65rem}.kodus-changelog-date{color:inherit;font:inherit;font-weight:600;line-height:inherit}.kodus-changelog-rss-source{display:none}.kodus-changelog-content{min-width:0;max-width:36rem}.kodus-changelog-shell{position:relative}.kodus-changelog-filter-panel{margin-top:0}.kodus-changelog-filter-control{position:absolute;inset:0;z-index:1;width:100%;height:100%;margin:0;appearance:none;border:1px solid transparent;border-radius:inherit;background:transparent;cursor:pointer}.kodus-changelog-filter-sidebar{position:fixed;top:12rem;right:max(2rem, calc((100vw - 88rem) / 2 + 2rem));width:20rem;z-index:9999;pointer-events:auto}.kodus-changelog-filter-heading{margin:0 0 0.7rem;color:#faf8f6;font:inherit;font-size:0.78em;font-weight:600;line-height:1.2}.kodus-changelog-filter-options{display:flex;flex-wrap:wrap;gap:0.55rem}.kodus-changelog-filter-button{position:relative;display:inline-flex;align-items:center;min-height:1.85rem;border:0;border-radius:999px;background:rgba(255, 255, 255, 0.06);color:inherit;cursor:pointer;padding:0.24rem 0.78rem;font:inherit;font-size:0.78em;font-weight:500;line-height:1;white-space:nowrap;user-select:none;overflow:hidden;transition:background-color 140ms ease,\n color 140ms ease}.kodus-changelog-filter-button span{position:relative;z-index:2;pointer-events:none}.kodus-changelog-filter-button:hover .kodus-changelog-filter-control:not(:checked){background:rgba(248, 183, 109, 0.12)}.kodus-changelog-filter-button:hover span{color:#f8b76d}.kodus-changelog-filter-button.is-selected,.kodus-changelog-filter-button:has(.kodus-changelog-filter-control:checked){border-color:rgba(248, 183, 109, 0.22)!important;background:rgba(248, 183, 109, 0.14)!important;color:#f8b76d!important}.kodus-changelog-filter-control:checked{border-color:rgba(248, 183, 109, 0.22)!important;background:rgba(248, 183, 109, 0.14)!important}.kodus-changelog-filter-control:checked+span{color:#f8b76d!important}.kodus-changelog-shell:has(.kodus-changelog-filter-control:checked) .kodus-changelog-filterable,.kodus-changelog-shell:has(.kodus-changelog-filter-control:checked) .kodus-changelog-section{display:none}.kodus-changelog-shell:has(.kodus-changelog-filter-control:checked) .kodus-changelog-release{display:none}.kodus-changelog-shell:has(#kodus-filter-security:checked) .filter-security,.kodus-changelog-shell:has(#kodus-filter-cockpit:checked) .filter-cockpit,.kodus-changelog-shell:has(#kodus-filter-byok:checked) .filter-byok,.kodus-changelog-shell:has(#kodus-filter-ai-engine:checked) .filter-ai-engine,.kodus-changelog-shell:has(#kodus-filter-self-hosted:checked) .filter-self-hosted,.kodus-changelog-shell:has(#kodus-filter-git-provider:checked) .filter-git-provider,.kodus-changelog-shell:has(#kodus-filter-performance:checked) .filter-performance,.kodus-changelog-shell:has(#kodus-filter-ux-interface:checked) .filter-ux-interface,.kodus-changelog-shell:has(#kodus-filter-notifications:checked) .filter-notifications,.kodus-changelog-shell:has(#kodus-filter-kody-rules:checked) .filter-kody-rules,.kodus-changelog-shell:has(#kodus-filter-mcp:checked) .filter-mcp,.kodus-changelog-shell:has(#kodus-filter-custom-agents:checked) .filter-custom-agents,.kodus-changelog-shell:has(#kodus-filter-billing-licenses:checked) .filter-billing-licenses,.kodus-changelog-shell:has(#kodus-filter-cli:checked) .filter-cli,.kodus-changelog-shell:has(#kodus-filter-security:checked) .kodus-changelog-section:has(.filter-security),.kodus-changelog-shell:has(#kodus-filter-cockpit:checked) .kodus-changelog-section:has(.filter-cockpit),.kodus-changelog-shell:has(#kodus-filter-byok:checked) .kodus-changelog-section:has(.filter-byok),.kodus-changelog-shell:has(#kodus-filter-ai-engine:checked) .kodus-changelog-section:has(.filter-ai-engine),.kodus-changelog-shell:has(#kodus-filter-self-hosted:checked) .kodus-changelog-section:has(.filter-self-hosted),.kodus-changelog-shell:has(#kodus-filter-git-provider:checked) .kodus-changelog-section:has(.filter-git-provider),.kodus-changelog-shell:has(#kodus-filter-performance:checked) .kodus-changelog-section:has(.filter-performance),.kodus-changelog-shell:has(#kodus-filter-ux-interface:checked) .kodus-changelog-section:has(.filter-ux-interface),.kodus-changelog-shell:has(#kodus-filter-notifications:checked) .kodus-changelog-section:has(.filter-notifications),.kodus-changelog-shell:has(#kodus-filter-kody-rules:checked) .kodus-changelog-section:has(.filter-kody-rules),.kodus-changelog-shell:has(#kodus-filter-mcp:checked) .kodus-changelog-section:has(.filter-mcp),.kodus-changelog-shell:has(#kodus-filter-custom-agents:checked) .kodus-changelog-section:has(.filter-custom-agents),.kodus-changelog-shell:has(#kodus-filter-billing-licenses:checked) .kodus-changelog-section:has(.filter-billing-licenses),.kodus-changelog-shell:has(#kodus-filter-cli:checked) .kodus-changelog-section:has(.filter-cli){display:block}.kodus-changelog-shell:has(#kodus-filter-security:checked) .kodus-changelog-release:has(.filter-security),.kodus-changelog-shell:has(#kodus-filter-cockpit:checked) .kodus-changelog-release:has(.filter-cockpit),.kodus-changelog-shell:has(#kodus-filter-byok:checked) .kodus-changelog-release:has(.filter-byok),.kodus-changelog-shell:has(#kodus-filter-ai-engine:checked) .kodus-changelog-release:has(.filter-ai-engine),.kodus-changelog-shell:has(#kodus-filter-self-hosted:checked) .kodus-changelog-release:has(.filter-self-hosted),.kodus-changelog-shell:has(#kodus-filter-git-provider:checked) .kodus-changelog-release:has(.filter-git-provider),.kodus-changelog-shell:has(#kodus-filter-performance:checked) .kodus-changelog-release:has(.filter-performance),.kodus-changelog-shell:has(#kodus-filter-ux-interface:checked) .kodus-changelog-release:has(.filter-ux-interface),.kodus-changelog-shell:has(#kodus-filter-notifications:checked) .kodus-changelog-release:has(.filter-notifications),.kodus-changelog-shell:has(#kodus-filter-kody-rules:checked) .kodus-changelog-release:has(.filter-kody-rules),.kodus-changelog-shell:has(#kodus-filter-mcp:checked) .kodus-changelog-release:has(.filter-mcp),.kodus-changelog-shell:has(#kodus-filter-custom-agents:checked) .kodus-changelog-release:has(.filter-custom-agents),.kodus-changelog-shell:has(#kodus-filter-billing-licenses:checked) .kodus-changelog-release:has(.filter-billing-licenses),.kodus-changelog-shell:has(#kodus-filter-cli:checked) .kodus-changelog-release:has(.filter-cli){display:grid}.kodus-changelog-empty{display:none;margin:0;color:inherit;font:inherit;line-height:inherit}.kodus-changelog-section+.kodus-changelog-section{margin-top:3rem;padding-top:2rem;border-top:1px solid rgba(248, 183, 109, 0.16)}.kodus-changelog-section-label{display:block;margin:0 0 2rem;color:#f8b76d;font:inherit;font-size:1em;font-weight:700;letter-spacing:0;line-height:inherit;text-transform:none}.kodus-changelog-item+.kodus-changelog-item{margin-top:2.5rem}.kodus-changelog-copy+.kodus-changelog-title,.kodus-changelog-list+.kodus-changelog-title,.kodus-changelog-video+.kodus-changelog-title{margin-top:1.75rem}.kodus-changelog-title{margin:0;color:#ffffff;font:inherit;font-size:1.25em;font-weight:700;letter-spacing:0;line-height:1.35}.kodus-changelog-copy{display:block;margin:0.85rem 0 0;color:inherit;font:inherit;line-height:inherit}.kodus-changelog-link{color:#f8b76d;font-weight:700;text-decoration:underline;text-decoration-color:rgba(248, 183, 109, 0.7);text-underline-offset:0.2em}.kodus-changelog-code{border-radius:0.35rem;background:rgba(248, 183, 109, 0.14);color:#f8b76d;padding:0.1rem 0.35rem;font-size:0.9em}.kodus-changelog-video{display:block;width:100%;margin:1.25rem 0 0;border:1px solid rgba(248, 183, 109, 0.22);border-radius:8px;background:rgba(0, 0, 0, 0.25)}.kodus-changelog-list{margin:0.85rem 0 0;padding-left:1.25rem;color:inherit;font:inherit;line-height:inherit}.kodus-changelog-list li+li{margin-top:0.5rem}.kodus-changelog-fix-list{margin-top:0.85rem}.kodus-changelog-fix{padding-left:1.25rem;position:relative}.kodus-changelog-fix .kodus-changelog-copy{margin-top:0}.kodus-changelog-fix-label{color:#ffffff;font-weight:700}.kodus-changelog-fix::before{content:\"\";position:absolute;top:0.75em;left:0.15rem;width:0.35rem;height:0.35rem;border-radius:999px;background:currentColor;opacity:0.68}.kodus-changelog-fix+.kodus-changelog-fix{margin-top:1.1rem}@media (max-width: 1120px){.kodus-changelog-release{grid-template-columns:6.5rem minmax(0, 1fr);column-gap:1.25rem}.kodus-changelog-filter-sidebar{grid-column:1 / -1;grid-row:1;position:static;margin-bottom:1.5rem;width:auto}.kodus-changelog-meta{grid-column:1;grid-row:2}.kodus-changelog-content{grid-column:2;grid-row:2}}@media (prefers-color-scheme: light){.kodus-changelog-title{color:#111827}.kodus-changelog-fix-label{color:#111827}}"}],"page":{"pagePath":"es/how_to_deploy/deploy_kodus/analytics_worker","slug":"/es/how_to_deploy/deploy_kodus/analytics_worker","pageMetadata":{"title":"Analytics Worker","description":"Worker de ingestión de analytics opcional para self-hosted Enterprise. Alimenta los dashboards del Cockpit (DORA, ciclo de vida, classifier).","icon":"chart-line","tag":"enterprise","href":"/es/how_to_deploy/deploy_kodus/analytics_worker"},"description":{"compiledSource":"\"use strict\";\nconst {jsx: _jsx} = arguments[0];\nconst {useMDXComponents: _provideComponents} = arguments[0];\nfunction _createMdxContent(props) {\n const _components = {\n p: \"p\",\n ..._provideComponents(),\n ...props.components\n };\n return _jsx(_components.p, {\n children: \"Worker de ingestión de analytics opcional para self-hosted Enterprise. Alimenta los dashboards del Cockpit (DORA, ciclo de vida, classifier).\"\n });\n}\nfunction MDXContent(props = {}) {\n const {wrapper: MDXLayout} = {\n ..._provideComponents(),\n ...props.components\n };\n return MDXLayout ? _jsx(MDXLayout, {\n ...props,\n children: _jsx(_createMdxContent, {\n ...props\n })\n }) : _createMdxContent(props);\n}\nreturn {\n default: MDXContent\n};\n","frontmatter":{},"scope":{}},"pageType":"default","mdx":{"mdxSource":{"compiledSource":"\"use strict\";const{Fragment:_Fragment,jsx:_jsx,jsxs:_jsxs}=arguments[0];const{useMDXComponents:_provideComponents}=arguments[0];function _createMdxContent(props){const _components={code:`code`,em:`em`,li:`li`,p:`p`,pre:`pre`,span:`span`,strong:`strong`,tbody:`tbody`,td:`td`,th:`th`,thead:`thead`,tr:`tr`,ul:`ul`,..._provideComponents(),...props.components},{CodeBlock,Heading,Mermaid,Table,Warning}=_components;if(!CodeBlock)_missingMdxReference(`CodeBlock`,true);if(!Heading)_missingMdxReference(`Heading`,true);if(!Mermaid)_missingMdxReference(`Mermaid`,true);if(!Table)_missingMdxReference(`Table`,true);if(!Warning)_missingMdxReference(`Warning`,true);return _jsxs(_Fragment,{children:[_jsxs(_components.p,{children:[`El analytics worker es un add-on `,_jsx(_components.strong,{children:`exclusivo de Enterprise`}),`. Ejecuta el\ncron de ingestión que alimenta los dashboards del Cockpit (métricas tipo\nDORA, ciclo de vida de PR, classifier de PR basado en LLM).`]}),`\n`,_jsx(Warning,{children:_jsxs(_components.p,{children:[`El instalador por defecto `,_jsx(_components.strong,{children:`no`}),` incluye este worker. Los despliegues\nself-hosted de la versión community no lo necesitan y estas vars se\nfiltran del `,_jsx(_components.code,{children:`.env.example`}),` por defecto. Detente aquí a menos que tengas\nuna licencia self-hosted Enterprise y quieras los reportes del Cockpit.`]})}),`\n`,_jsx(Heading,{level:`2`,id:`qué-hace`,children:`Qué hace`}),`\n`,_jsxs(_components.p,{children:[`Un proceso Node separado ejecutando la `,_jsxs(_components.strong,{children:[`misma imagen del `,_jsx(_components.code,{children:`worker`})]}),`\n(`,_jsx(_components.code,{children:`kodus-ai-worker`}),`), seleccionado en el boot vía `,_jsx(_components.code,{children:`WORKER_ROLE=analytics`}),`.\nDos crons disparan desde este proceso y solo desde él:`]}),`\n`,_jsxs(_components.ul,{children:[`\n`,_jsxs(_components.li,{children:[_jsx(_components.strong,{children:`Ingestión`}),` (`,_jsx(_components.code,{children:`ANALYTICS_INGESTION_CRON`}),`, default `,_jsx(_components.code,{children:`*/30 * * * *`}),`) — lee\npull requests y sesiones de review desde Mongo + el Postgres OLTP, y los\nproyecta al schema `,_jsx(_components.code,{children:`analytics`}),`.`]}),`\n`,_jsxs(_components.li,{children:[_jsx(_components.strong,{children:`Classifier`}),` (`,_jsx(_components.code,{children:`ANALYTICS_CLASSIFIER_CRON`}),`, default `,_jsx(_components.code,{children:`*/15 * * * *`}),`) —\nllama un LLM para etiquetar cada PR con un tipo (feature/bugfix/refactor/etc).`]}),`\n`]}),`\n`,_jsxs(_components.p,{children:[`Aislarlo del `,_jsx(_components.code,{children:`worker`}),` principal mantiene el event loop de code review\nlibre de queries de ingestión largas.`]}),`\n`,_jsx(Heading,{level:`2`,id:`topología`,children:`Topología`}),`\n`,_jsxs(_components.p,{children:[`El warehouse de analytics es un `,_jsx(_components.strong,{children:`schema`}),` de Postgres, no una base de\ndatos separada. Dos layouts soportados:`]}),`\n`,_jsxs(_components.ul,{children:[`\n`,_jsxs(_components.li,{children:[_jsx(_components.strong,{children:`Postgres compartido (recomendado para self-hosted)`}),` — deja\n`,_jsx(_components.code,{children:`ANALYTICS_PG_DB_HOST`}),` vacío. El config loader cae en el fallback de\nlas vars `,_jsx(_components.code,{children:`API_PG_DB_*`}),` y crea un schema `,_jsx(_components.code,{children:`analytics`}),` en la misma\ninstancia. Una sola DB para respaldar y operar.`]}),`\n`,_jsxs(_components.li,{children:[_jsx(_components.strong,{children:`Postgres dedicado`}),` — define el bloque `,_jsx(_components.code,{children:`ANALYTICS_PG_DB_*`}),` apuntando\na otra instancia. Úsalo cuando quieras queries analíticas totalmente\naisladas del write path del OLTP.`]}),`\n`]}),`\n`,_jsx(Mermaid,{chart:`flowchart LR\n api[api] --> pg[(Postgres OLTP)]\n worker[worker] --> rabbitmq[(RabbitMQ)]\n aw[worker-analytics] --> rabbitmq\n aw --> pg\n aw --> mg[(MongoDB)]\n aw -.->|escribe| analytics[(Postgres • schema analytics)]\n cockpit[Cockpit UI] --> analytics`}),`\n`,_jsx(Heading,{level:`2`,id:`habilitando-en-self-hosted-enterprise`,children:`Habilitando en self-hosted Enterprise`}),`\n`,_jsxs(Heading,{level:`3`,id:`1-agrega-el-servicio-a-docker-compose-yml`,children:[`1. Agrega el servicio a `,_jsx(_components.code,{children:`docker-compose.yml`})]}),`\n`,_jsx(CodeBlock,{filename:``,numberOfLines:`18`,language:`yaml`,children:_jsx(_components.pre,{className:`shiki shiki-themes github-light-default dark-plus`,style:{backgroundColor:`#ffffff`,\"--shiki-dark-bg\":`#0B0C0E`,color:`#1f2328`,\"--shiki-dark\":`#D4D4D4`},language:`yaml`,children:_jsxs(_components.code,{language:`yaml`,numberOfLines:`18`,children:[_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#116329`,\"--shiki-dark\":`#569CD6`},children:`worker-analytics`}),_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:`:`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#116329`,\"--shiki-dark\":`#569CD6`},children:` image`}),_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:`: `}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`ghcr.io/kodustech/kodus-ai-worker:latest`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#116329`,\"--shiki-dark\":`#569CD6`},children:` platform`}),_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:`: `}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`linux/amd64`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#116329`,\"--shiki-dark\":`#569CD6`},children:` container_name`}),_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:`: `}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`kodus-worker-analytics`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#116329`,\"--shiki-dark\":`#569CD6`},children:` environment`}),_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:`:`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:` - `}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`ENV=production`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:` - `}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`NODE_ENV=production`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:` - `}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`WORKER_ROLE=analytics`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#116329`,\"--shiki-dark\":`#569CD6`},children:` networks`}),_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:`:`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:` - `}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`shared-network`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:` - `}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`kodus-backend-services`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#116329`,\"--shiki-dark\":`#569CD6`},children:` restart`}),_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:`: `}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`unless-stopped`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#116329`,\"--shiki-dark\":`#569CD6`},children:` env_file`}),_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:`:`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:` - `}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`.env`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#116329`,\"--shiki-dark\":`#569CD6`},children:` depends_on`}),_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:`:`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:` - `}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`db_kodus_postgres`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:` - `}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`db_kodus_mongodb`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:` - `}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`rabbitmq`})]}),`\n`]})})}),`\n`,_jsxs(_components.p,{children:[`La imagen es idéntica al servicio `,_jsx(_components.code,{children:`worker`}),` — solo `,_jsx(_components.code,{children:`WORKER_ROLE=analytics`}),`\nlo cambia a modo ingestión.`]}),`\n`,_jsxs(Heading,{level:`3`,id:`2-agrega-el-bloque-de-analytics-al-env`,children:[`2. Agrega el bloque de analytics al `,_jsx(_components.code,{children:`.env`})]}),`\n`,_jsx(_components.p,{children:_jsx(_components.strong,{children:`Postgres compartido (recomendado):`})}),`\n`,_jsx(CodeBlock,{filename:``,numberOfLines:`8`,language:`shellscript`,children:_jsx(_components.pre,{className:`shiki shiki-themes github-light-default dark-plus`,style:{backgroundColor:`#ffffff`,\"--shiki-dark-bg\":`#0B0C0E`,color:`#1f2328`,\"--shiki-dark\":`#D4D4D4`},language:`shellscript`,children:_jsxs(_components.code,{language:`shellscript`,numberOfLines:`8`,children:[_jsx(_components.span,{className:`line`,children:_jsx(_components.span,{style:{color:`#6E7781`,\"--shiki-dark\":`#6A9955`},children:`# ANALYTICS_PG_DB_HOST vacío → el loader reutiliza API_PG_DB_* y crea`})}),`\n`,_jsx(_components.span,{className:`line`,children:_jsx(_components.span,{style:{color:`#6E7781`,\"--shiki-dark\":`#6A9955`},children:\"# el schema `analytics` en la instancia principal.\"})}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#9CDCFE`},children:`ANALYTICS_PG_DB_HOST`}),_jsx(_components.span,{style:{color:`#CF222E`,\"--shiki-dark\":`#D4D4D4`},children:`=`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#9CDCFE`},children:`ANALYTICS_PG_DB_SCHEMA`}),_jsx(_components.span,{style:{color:`#CF222E`,\"--shiki-dark\":`#D4D4D4`},children:`=`}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`analytics`})]}),`\n`,_jsx(_components.span,{className:`line`}),`\n`,_jsx(_components.span,{className:`line`,children:_jsx(_components.span,{style:{color:`#6E7781`,\"--shiki-dark\":`#6A9955`},children:`# Cron schedules (UTC).`})}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#9CDCFE`},children:`ANALYTICS_INGESTION_CRON`}),_jsx(_components.span,{style:{color:`#CF222E`,\"--shiki-dark\":`#D4D4D4`},children:`=`}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`*/30`}),_jsx(_components.span,{style:{color:`#953800`,\"--shiki-dark\":`#DCDCAA`},children:` *`}),_jsx(_components.span,{style:{color:`#0550AE`,\"--shiki-dark\":`#569CD6`},children:` *`}),_jsx(_components.span,{style:{color:`#0550AE`,\"--shiki-dark\":`#569CD6`},children:` *`}),_jsx(_components.span,{style:{color:`#0550AE`,\"--shiki-dark\":`#569CD6`},children:` *`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#9CDCFE`},children:`ANALYTICS_CLASSIFIER_CRON`}),_jsx(_components.span,{style:{color:`#CF222E`,\"--shiki-dark\":`#D4D4D4`},children:`=`}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`*/15`}),_jsx(_components.span,{style:{color:`#953800`,\"--shiki-dark\":`#DCDCAA`},children:` *`}),_jsx(_components.span,{style:{color:`#0550AE`,\"--shiki-dark\":`#569CD6`},children:` *`}),_jsx(_components.span,{style:{color:`#0550AE`,\"--shiki-dark\":`#569CD6`},children:` *`}),_jsx(_components.span,{style:{color:`#0550AE`,\"--shiki-dark\":`#569CD6`},children:` *`})]}),`\n`]})})}),`\n`,_jsx(_components.p,{children:_jsx(_components.strong,{children:`Postgres dedicado:`})}),`\n`,_jsx(CodeBlock,{filename:``,numberOfLines:`9`,language:`shellscript`,children:_jsx(_components.pre,{className:`shiki shiki-themes github-light-default dark-plus`,style:{backgroundColor:`#ffffff`,\"--shiki-dark-bg\":`#0B0C0E`,color:`#1f2328`,\"--shiki-dark\":`#D4D4D4`},language:`shellscript`,children:_jsxs(_components.code,{language:`shellscript`,numberOfLines:`9`,children:[_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#9CDCFE`},children:`ANALYTICS_PG_DB_HOST`}),_jsx(_components.span,{style:{color:`#CF222E`,\"--shiki-dark\":`#D4D4D4`},children:`=`}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`tu-host-de-analytics`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#9CDCFE`},children:`ANALYTICS_PG_DB_PORT`}),_jsx(_components.span,{style:{color:`#CF222E`,\"--shiki-dark\":`#D4D4D4`},children:`=`}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`5432`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#9CDCFE`},children:`ANALYTICS_PG_DB_USERNAME`}),_jsx(_components.span,{style:{color:`#CF222E`,\"--shiki-dark\":`#D4D4D4`},children:`=`}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`analytics`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#9CDCFE`},children:`ANALYTICS_PG_DB_PASSWORD`}),_jsx(_components.span,{style:{color:`#CF222E`,\"--shiki-dark\":`#D4D4D4`},children:`=`}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`...`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#9CDCFE`},children:`ANALYTICS_PG_DB_DATABASE`}),_jsx(_components.span,{style:{color:`#CF222E`,\"--shiki-dark\":`#D4D4D4`},children:`=`}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`kodus_analytics`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#9CDCFE`},children:`ANALYTICS_PG_DB_SCHEMA`}),_jsx(_components.span,{style:{color:`#CF222E`,\"--shiki-dark\":`#D4D4D4`},children:`=`}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`analytics`})]}),`\n`,_jsx(_components.span,{className:`line`}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#9CDCFE`},children:`ANALYTICS_INGESTION_CRON`}),_jsx(_components.span,{style:{color:`#CF222E`,\"--shiki-dark\":`#D4D4D4`},children:`=`}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`*/30`}),_jsx(_components.span,{style:{color:`#953800`,\"--shiki-dark\":`#DCDCAA`},children:` *`}),_jsx(_components.span,{style:{color:`#0550AE`,\"--shiki-dark\":`#569CD6`},children:` *`}),_jsx(_components.span,{style:{color:`#0550AE`,\"--shiki-dark\":`#569CD6`},children:` *`}),_jsx(_components.span,{style:{color:`#0550AE`,\"--shiki-dark\":`#569CD6`},children:` *`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#9CDCFE`},children:`ANALYTICS_CLASSIFIER_CRON`}),_jsx(_components.span,{style:{color:`#CF222E`,\"--shiki-dark\":`#D4D4D4`},children:`=`}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`*/15`}),_jsx(_components.span,{style:{color:`#953800`,\"--shiki-dark\":`#DCDCAA`},children:` *`}),_jsx(_components.span,{style:{color:`#0550AE`,\"--shiki-dark\":`#569CD6`},children:` *`}),_jsx(_components.span,{style:{color:`#0550AE`,\"--shiki-dark\":`#569CD6`},children:` *`}),_jsx(_components.span,{style:{color:`#0550AE`,\"--shiki-dark\":`#569CD6`},children:` *`})]}),`\n`]})})}),`\n`,_jsx(Heading,{level:`3`,id:`3-boot-—-las-migrations-corren-automáticamente`,children:`3. Boot — las migrations corren automáticamente`}),`\n`,_jsxs(_components.p,{children:[`El contenedor `,_jsx(_components.code,{children:`worker-analytics`}),` comparte el mismo `,_jsx(_components.code,{children:`prod-entrypoint.sh`}),`\nque `,_jsx(_components.code,{children:`api`}),`/`,_jsx(_components.code,{children:`worker`}),`/`,_jsx(_components.code,{children:`webhooks`}),`. Con `,_jsx(_components.code,{children:`RUN_MIGRATIONS=true`}),` (default del\ninstaller), las migrations del warehouse de analytics\n(`,_jsx(_components.code,{children:`pnpm run analytics:migration:run:prod`}),`) corren en el primer boot, creando\nel schema `,_jsx(_components.code,{children:`analytics`}),` y sus tablas.`]}),`\n`,_jsx(Heading,{level:`2`,id:`referencia`,children:`Referencia`}),`\n`,_jsxs(Table,{children:[_jsx(_components.thead,{children:_jsxs(_components.tr,{children:[_jsx(_components.th,{children:`Variable`}),_jsx(_components.th,{children:`Descripción`}),_jsx(_components.th,{children:`Default`})]})}),_jsxs(_components.tbody,{children:[_jsxs(_components.tr,{children:[_jsx(_components.td,{children:_jsx(_components.code,{children:`WORKER_ROLE`})}),_jsxs(_components.td,{children:[`Debe estar en `,_jsx(_components.code,{children:`analytics`}),` en este contenedor.`]}),_jsx(_components.td,{children:_jsx(_components.em,{children:`requerido`})})]}),_jsxs(_components.tr,{children:[_jsx(_components.td,{children:_jsx(_components.code,{children:`ANALYTICS_PG_DB_HOST`})}),_jsx(_components.td,{children:`Host del Postgres de analytics. Vacío → reutiliza el Postgres principal.`}),_jsx(_components.td,{children:_jsx(_components.em,{children:`vacío`})})]}),_jsxs(_components.tr,{children:[_jsx(_components.td,{children:_jsx(_components.code,{children:`ANALYTICS_PG_DB_PORT`})}),_jsx(_components.td,{children:`Puerto del Postgres de analytics.`}),_jsx(_components.td,{\"data-numeric\":`true`,children:_jsx(_components.code,{children:`5432`})})]}),_jsxs(_components.tr,{children:[_jsx(_components.td,{children:_jsx(_components.code,{children:`ANALYTICS_PG_DB_USERNAME`})}),_jsxs(_components.td,{children:[`Usuario del Postgres de analytics. Vacío → reutiliza `,_jsx(_components.code,{children:`API_PG_DB_USERNAME`}),`.`]}),_jsx(_components.td,{children:_jsx(_components.em,{children:`vacío`})})]}),_jsxs(_components.tr,{children:[_jsx(_components.td,{children:_jsx(_components.code,{children:`ANALYTICS_PG_DB_PASSWORD`})}),_jsxs(_components.td,{children:[`Contraseña del Postgres de analytics. Vacío → reutiliza `,_jsx(_components.code,{children:`API_PG_DB_PASSWORD`}),`.`]}),_jsx(_components.td,{children:_jsx(_components.em,{children:`vacío`})})]}),_jsxs(_components.tr,{children:[_jsx(_components.td,{children:_jsx(_components.code,{children:`ANALYTICS_PG_DB_DATABASE`})}),_jsxs(_components.td,{children:[`Base del Postgres de analytics. Vacío → reutiliza `,_jsx(_components.code,{children:`API_PG_DB_DATABASE`}),`.`]}),_jsx(_components.td,{children:_jsx(_components.em,{children:`vacío`})})]}),_jsxs(_components.tr,{children:[_jsx(_components.td,{children:_jsx(_components.code,{children:`ANALYTICS_PG_DB_SCHEMA`})}),_jsx(_components.td,{children:`Nombre del schema de las tablas del warehouse.`}),_jsx(_components.td,{children:_jsx(_components.code,{children:`analytics`})})]}),_jsxs(_components.tr,{children:[_jsx(_components.td,{children:_jsx(_components.code,{children:`ANALYTICS_PG_POOL_MAX`})}),_jsx(_components.td,{children:`Límite superior del pool del Postgres de analytics.`}),_jsx(_components.td,{\"data-numeric\":`true`,children:_jsx(_components.code,{children:`5`})})]}),_jsxs(_components.tr,{children:[_jsx(_components.td,{children:_jsx(_components.code,{children:`ANALYTICS_INGESTION_CRON`})}),_jsx(_components.td,{children:`Cron schedule de la ingestión (UTC).`}),_jsx(_components.td,{children:_jsx(_components.code,{children:`*/30 * * * *`})})]}),_jsxs(_components.tr,{children:[_jsx(_components.td,{children:_jsx(_components.code,{children:`ANALYTICS_CLASSIFIER_CRON`})}),_jsx(_components.td,{children:`Cron schedule del classifier de tipo de PR vía LLM (UTC).`}),_jsx(_components.td,{children:_jsx(_components.code,{children:`*/15 * * * *`})})]})]})]}),`\n`,_jsx(Heading,{level:`3`,id:`pausando-la-ingestión-avanzado`,children:`Pausando la ingestión (avanzado)`}),`\n`,_jsxs(_components.p,{children:[`Para detener la ingestión en runtime sin remover el contenedor, define\n`,_jsx(_components.code,{children:`ANALYTICS_INGESTION_DISABLED=true`}),` y/o `,_jsx(_components.code,{children:`ANALYTICS_CLASSIFIER_DISABLED=true`}),`\ny reinicia `,_jsx(_components.code,{children:`worker-analytics`}),`. El cron sigue agendado pero cada tick\nhace short-circuit. Úsalo para triaje de incidentes, no como config a\nlargo plazo — esas vars se gestionan principalmente para cloud y pueden\nno aparecer en el template del installer.`]}),`\n`,_jsx(Heading,{level:`2`,id:`verificando-que-funciona`,children:`Verificando que funciona`}),`\n`,_jsx(_components.p,{children:`Después del boot, sigue los logs del analytics worker:`}),`\n`,_jsx(CodeBlock,{filename:``,numberOfLines:`1`,language:`shellscript`,children:_jsx(_components.pre,{className:`shiki shiki-themes github-light-default dark-plus`,style:{backgroundColor:`#ffffff`,\"--shiki-dark-bg\":`#0B0C0E`,color:`#1f2328`,\"--shiki-dark\":`#D4D4D4`},language:`shellscript`,children:_jsxs(_components.code,{language:`shellscript`,numberOfLines:`1`,children:[_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#953800`,\"--shiki-dark\":`#DCDCAA`},children:`docker`}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:` compose`}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:` logs`}),_jsx(_components.span,{style:{color:`#0550AE`,\"--shiki-dark\":`#569CD6`},children:` -f`}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:` worker-analytics`})]}),`\n`]})})}),`\n`,_jsxs(_components.p,{children:[`Debes ver líneas como `,_jsx(_components.code,{children:`analytics ingestion done in NNNms — {...}`}),` cada\n30 minutos y `,_jsx(_components.code,{children:`analytics classifier done ...`}),` cada 15 minutos. Si no,\nconfirma que `,_jsx(_components.code,{children:`WORKER_ROLE=analytics`}),` está seteado solo en este\ncontenedor (no en el `,_jsx(_components.code,{children:`worker`}),` principal — ese debe permanecer en\n`,_jsx(_components.code,{children:`code-review`}),`).`]})]})}function MDXContent(props={}){const{wrapper:MDXLayout}={..._provideComponents(),...props.components};return MDXLayout?_jsx(MDXLayout,{...props,children:_jsx(_createMdxContent,{...props})}):_createMdxContent(props)}return{default:MDXContent};function _missingMdxReference(id,component){throw new Error(`Expected `+(component?`component`:`object`)+\" `\"+id+\"` to be defined: you likely forgot to import, pass, or provide it.\")}","frontmatter":{},"scope":{"config":{},"pageMetadata":{"title":"Analytics Worker","description":"Worker de ingestión de analytics opcional para self-hosted Enterprise. Alimenta los dashboards del Cockpit (DORA, ciclo de vida, classifier).","icon":"chart-line","tag":"enterprise","href":"/es/how_to_deploy/deploy_kodus/analytics_worker"}}},"mdxSourceWithNoJs":null},"mdxExtracts":{"tableOfContents":[{"title":"Qué hace","slug":"qué-hace","depth":2,"children":[]},{"title":"Topología","slug":"topología","depth":2,"children":[]},{"title":"Habilitando en self-hosted Enterprise","slug":"habilitando-en-self-hosted-enterprise","depth":2,"children":[{"title":"1. Agrega el servicio a docker-compose.yml","slug":"1-agrega-el-servicio-a-docker-compose-yml","depth":3,"children":[]},{"title":"2. Agrega el bloque de analytics al .env","slug":"2-agrega-el-bloque-de-analytics-al-env","depth":3,"children":[]},{"title":"3. Boot — las migrations corren automáticamente","slug":"3-boot-—-las-migrations-corren-automáticamente","depth":3,"children":[]}]},{"title":"Referencia","slug":"referencia","depth":2,"children":[{"title":"Pausando la ingestión (avanzado)","slug":"pausando-la-ingestión-avanzado","depth":3,"children":[]}]},{"title":"Verificando que funciona","slug":"verificando-que-funciona","depth":2,"children":[]}],"codeExamples":{}},"jsLinks":[],"subdomain":"kodus","siteName":"Kodus","title":"Analytics Worker - Kodus","navMaps":{"firstHrefInVersion":{},"firstHrefInLanguage":{"en":{"href":"/en/how_to_deploy/deploy_kodus/analytics_worker","matchLevel":1},"es":{"href":"/es/how_to_deploy/deploy_kodus/analytics_worker","matchLevel":0},"pt-BR":{"href":"/pt-BR/how_to_deploy/deploy_kodus/analytics_worker","matchLevel":1},"ja":{"href":"/ja/how_to_deploy/deploy_kodus/analytics_worker","matchLevel":1},"zh":{"href":"/zh/how_to_deploy/deploy_kodus/analytics_worker","matchLevel":1}}},"lastModified":"2026-09-25T17:42:32.050Z","originalFileLocation":"es/how_to_deploy/deploy_kodus/analytics_worker.mdx","locale":"es"},"headHtml":"\u003cscript data-mint-head>(function(){var d=document.documentElement,p=null;if(!p){try{p=localStorage.getItem(\"isDarkMode\")}catch(e){}if(p==='true')p='dark';else if(p==='false')p='light';if(p!=='light'\u0026\u0026p!=='dark'\u0026\u0026p!=='system')p=\"system\"}var r=p==='system'?(matchMedia(\"(prefers-color-scheme: dark)\").matches?'dark':'light'):p;d.classList.remove(r==='dark'?'light':'dark');d.classList.add(r);d.setAttribute(\"data-theme-preference\",p)})();\u003c/script>\u003cmeta data-mint-head name=\"description\" content=\"Worker de ingestión de analytics opcional para self-hosted Enterprise. Alimenta los dashboards del Cockpit (DORA, ciclo de vida, classifier).\">\u003cmeta data-mint-head name=\"application-name\" content=\"Kodus\">\u003cmeta data-mint-head name=\"generator\" content=\"Mintlify\">\u003clink data-mint-head rel=\"icon\" type=\"image/png\" sizes=\"192x192\" href=\"/mintlify-assets/_mintlify/favicons/kodus/PQ3FvCcQd6QjpCLU/_generated/favicon/android-chrome-192x192.png\" media=\"(prefers-color-scheme: light)\">\u003clink data-mint-head rel=\"apple-touch-icon\" type=\"image/png\" sizes=\"180x180\" href=\"/mintlify-assets/_mintlify/favicons/kodus/PQ3FvCcQd6QjpCLU/_generated/favicon/apple-touch-icon.png\">\u003clink data-mint-head rel=\"icon\" type=\"image/png\" sizes=\"16x16\" href=\"/mintlify-assets/_mintlify/favicons/kodus/PQ3FvCcQd6QjpCLU/_generated/favicon/favicon-16x16.png\" media=\"(prefers-color-scheme: light)\">\u003clink data-mint-head rel=\"icon\" type=\"image/png\" sizes=\"32x32\" href=\"/mintlify-assets/_mintlify/favicons/kodus/PQ3FvCcQd6QjpCLU/_generated/favicon/favicon-32x32.png\" media=\"(prefers-color-scheme: light)\">\u003clink data-mint-head rel=\"shortcut icon\" type=\"image/x-icon\" href=\"/mintlify-assets/_mintlify/favicons/kodus/PQ3FvCcQd6QjpCLU/_generated/favicon/favicon.ico\" media=\"(prefers-color-scheme: light)\">\u003clink data-mint-head rel=\"icon\" type=\"image/png\" sizes=\"192x192\" href=\"/mintlify-assets/_mintlify/favicons/kodus/PQ3FvCcQd6QjpCLU/_generated/favicon-dark/android-chrome-192x192.png\" media=\"(prefers-color-scheme: dark)\">\u003clink data-mint-head rel=\"icon\" type=\"image/png\" sizes=\"16x16\" href=\"/mintlify-assets/_mintlify/favicons/kodus/PQ3FvCcQd6QjpCLU/_generated/favicon-dark/favicon-16x16.png\" media=\"(prefers-color-scheme: dark)\">\u003clink data-mint-head rel=\"icon\" type=\"image/png\" sizes=\"32x32\" href=\"/mintlify-assets/_mintlify/favicons/kodus/PQ3FvCcQd6QjpCLU/_generated/favicon-dark/favicon-32x32.png\" media=\"(prefers-color-scheme: dark)\">\u003clink data-mint-head rel=\"shortcut icon\" type=\"image/x-icon\" href=\"/mintlify-assets/_mintlify/favicons/kodus/PQ3FvCcQd6QjpCLU/_generated/favicon-dark/favicon.ico\" media=\"(prefers-color-scheme: dark)\">\u003cmeta data-mint-head property=\"og:title\" content=\"Analytics Worker - Kodus\">\u003cmeta data-mint-head property=\"og:description\" content=\"Worker de ingestión de analytics opcional para self-hosted Enterprise. Alimenta los dashboards del Cockpit (DORA, ciclo de vida, classifier).\">\u003cmeta data-mint-head property=\"og:site_name\" content=\"Kodus\">\u003cmeta data-mint-head property=\"og:url\" content=\"https://docs.kodus.io/es/how_to_deploy/deploy_kodus/analytics_worker\">\u003cmeta data-mint-head property=\"og:type\" content=\"website\">\u003cmeta data-mint-head property=\"og:image\" content=\"https://kodus.mintlify.app/_mintlify/api/og/v2?division=Despliegue+con+Docker\u0026amp;title=Analytics+Worker\u0026amp;description=Worker+de+ingesti%C3%B3n+de+analytics+opcional+para+self-hosted+Enterprise.+Alimenta+los+dashboards+del+Cockpit+%28DORA%2C+ciclo+de+vida%2C+classifier%29.\u0026amp;theme=04a77bbc4db3cb7cb013f7f3\u0026amp;signature=e961f47bb592f9e52e707bb18952fd608a11718992d6769dc30b3adf76fe4c5c\">\u003cmeta data-mint-head property=\"og:image:width\" content=\"1200\">\u003cmeta data-mint-head property=\"og:image:height\" content=\"630\">\u003cmeta data-mint-head name=\"twitter:card\" content=\"summary_large_image\">\u003cmeta data-mint-head name=\"twitter:title\" content=\"Analytics Worker - Kodus\">\u003cmeta data-mint-head name=\"twitter:description\" content=\"Worker de ingestión de analytics opcional para self-hosted Enterprise. Alimenta los dashboards del Cockpit (DORA, ciclo de vida, classifier).\">\u003cmeta data-mint-head name=\"twitter:image\" content=\"https://kodus.mintlify.app/_mintlify/api/og/v2?division=Despliegue+con+Docker\u0026amp;title=Analytics+Worker\u0026amp;description=Worker+de+ingesti%C3%B3n+de+analytics+opcional+para+self-hosted+Enterprise.+Alimenta+los+dashboards+del+Cockpit+%28DORA%2C+ciclo+de+vida%2C+classifier%29.\u0026amp;theme=04a77bbc4db3cb7cb013f7f3\u0026amp;signature=e961f47bb592f9e52e707bb18952fd608a11718992d6769dc30b3adf76fe4c5c\">\u003cmeta data-mint-head name=\"twitter:image:width\" content=\"1200\">\u003cmeta data-mint-head name=\"twitter:image:height\" content=\"630\">\u003cmeta data-mint-head name=\"msapplication-config\" content=\"/mintlify-assets/_mintlify/favicons/kodus/PQ3FvCcQd6QjpCLU/_generated/favicon/browserconfig.xml\">\u003cmeta data-mint-head name=\"apple-mobile-web-app-title\" content=\"Kodus\">\u003cmeta data-mint-head name=\"msapplication-TileColor\" content=\"#F8B76D\">\u003clink data-mint-head rel=\"canonical\" href=\"https://docs.kodus.io/es/how_to_deploy/deploy_kodus/analytics_worker\">\u003clink data-mint-head rel=\"alternate\" type=\"application/xml\" href=\"/sitemap.xml\">\u003clink data-mint-head rel=\"alternate\" type=\"text/markdown\" href=\"/es/how_to_deploy/deploy_kodus/analytics_worker.md\">\u003clink data-mint-head rel=\"alternate\" hreflang=\"es\" href=\"https://docs.kodus.io/es/how_to_deploy/deploy_kodus/analytics_worker\">\u003clink data-mint-head rel=\"alternate\" hreflang=\"en\" href=\"https://docs.kodus.io/en/how_to_deploy/deploy_kodus/analytics_worker\">\u003clink data-mint-head rel=\"alternate\" hreflang=\"pt-BR\" href=\"https://docs.kodus.io/pt-BR/how_to_deploy/deploy_kodus/analytics_worker\">\u003clink data-mint-head rel=\"alternate\" hreflang=\"ja\" href=\"https://docs.kodus.io/ja/how_to_deploy/deploy_kodus/analytics_worker\">\u003clink data-mint-head rel=\"alternate\" hreflang=\"zh\" href=\"https://docs.kodus.io/zh/how_to_deploy/deploy_kodus/analytics_worker\">\u003clink data-mint-head rel=\"alternate\" hreflang=\"x-default\" href=\"https://docs.kodus.io/en/how_to_deploy/deploy_kodus/analytics_worker\">\u003cscript data-mint-head type=\"application/ld+json\">{\"@context\":\"https://schema.org\",\"@graph\":[{\"@type\":\"Organization\",\"@id\":\"https://docs.kodus.io/#organization\",\"name\":\"Kodus\",\"url\":\"https://docs.kodus.io\",\"logo\":{\"@type\":\"ImageObject\",\"url\":\"https://mintcdn.com/kodus/AF97E4sqQ0bDm2vv/logo/light.svg?fit=max\u0026auto=format\u0026n=AF97E4sqQ0bDm2vv\u0026q=85\u0026s=f936e2273166bb149af32c25f012a088\"}},{\"@type\":\"WebSite\",\"@id\":\"https://docs.kodus.io#website\",\"name\":\"Kodus\",\"url\":\"https://docs.kodus.io\",\"publisher\":{\"@id\":\"https://docs.kodus.io/#organization\"}},{\"@type\":\"WebPage\",\"@id\":\"https://docs.kodus.io/es/how_to_deploy/deploy_kodus/analytics_worker#webpage\",\"url\":\"https://docs.kodus.io/es/how_to_deploy/deploy_kodus/analytics_worker\",\"name\":\"Analytics Worker\",\"description\":\"Worker de ingestión de analytics opcional para self-hosted Enterprise. Alimenta los dashboards del Cockpit (DORA, ciclo de vida, classifier).\",\"dateModified\":\"2026-09-25T17:42:32.050Z\",\"isPartOf\":{\"@id\":\"https://docs.kodus.io#website\"},\"breadcrumb\":{\"@id\":\"https://docs.kodus.io/es/how_to_deploy/deploy_kodus/analytics_worker#breadcrumb\"}},{\"@type\":\"BreadcrumbList\",\"@id\":\"https://docs.kodus.io/es/how_to_deploy/deploy_kodus/analytics_worker#breadcrumb\",\"itemListElement\":[{\"@type\":\"ListItem\",\"position\":1,\"name\":\"Despliegue con Docker\",\"item\":\"https://docs.kodus.io/es/how_to_deploy/deploy_kodus/generic_vm\"},{\"@type\":\"ListItem\",\"position\":2,\"name\":\"Analytics Worker\",\"item\":\"https://docs.kodus.io/es/how_to_deploy/deploy_kodus/analytics_worker\"}]},{\"@type\":[\"Article\",\"TechArticle\"],\"@id\":\"https://docs.kodus.io/es/how_to_deploy/deploy_kodus/analytics_worker#article\",\"headline\":\"Analytics Worker\",\"name\":\"Analytics Worker\",\"description\":\"Worker de ingestión de analytics opcional para self-hosted Enterprise. Alimenta los dashboards del Cockpit (DORA, ciclo de vida, classifier).\",\"url\":\"https://docs.kodus.io/es/how_to_deploy/deploy_kodus/analytics_worker\",\"mainEntityOfPage\":{\"@id\":\"https://docs.kodus.io/es/how_to_deploy/deploy_kodus/analytics_worker#webpage\"},\"dateModified\":\"2026-09-25T17:42:32.050Z\",\"publisher\":{\"@id\":\"https://docs.kodus.io/#organization\"},\"isPartOf\":{\"@id\":\"https://docs.kodus.io#website\"}}]}\u003c/script>\u003cscript data-mint-head type=\"application/ld+json\">{\"@context\":\"https://schema.org\",\"@type\":\"WebSite\",\"name\":\"Kodus\",\"creator\":{\"@type\":\"Organization\",\"name\":\"Mintlify\",\"url\":\"https://mintlify.com\"}}\u003c/script>","siteName":"Kodus","nav":{"global":null,"languages":[{"language":"en","pages":[{"title":"en","href":"/en/how_to_deploy/deploy_kodus/analytics_worker"}]},{"language":"es","tabs":[{"tab":"Cómo usar","icon":"gamepad-modern","pages":[{"title":"Cómo usar","href":"/es/how_to_use/overview"}]},{"tab":"Cómo desplegar","icon":"rocket-launch","groups":[{"group":"Conceptos","pages":[{"title":"Arquitectura de Kodus","icon":"puzzle-piece","href":"/es/how_to_deploy/kodus_architecture"}]},{"group":"Inicio Rápido Local","pages":[{"title":"Inicio rápido local","icon":"laptop","href":"/es/how_to_deploy/local_quickstart/orchestrator"}]},{"group":"Despliegue con Docker","pages":[{"title":"Instalación","icon":"plug","href":"/es/how_to_deploy/deploy_kodus/generic_vm"},{"title":"MCP Manager","icon":"puzzle-piece","tag":"beta","href":"/es/how_to_deploy/deploy_kodus/mcp_manager"},{"title":"Sandbox \u0026 AST Graph","description":"Cómo Kodus parsea tu repo (kodus-graph), dónde se ejecuta (modos de sandbox), y cuándo elegir cada modo.","icon":"box","href":"/es/how_to_deploy/deploy_kodus/sandbox"},{"title":"Analytics Worker","icon":"chart-line","tag":"enterprise","href":"/es/how_to_deploy/deploy_kodus/analytics_worker"},{"title":"Proxy inverso","description":"Configura un proxy inverso para Kodus.","icon":"server","href":"/es/how_to_deploy/deploy_kodus/reverse_proxy"},{"title":"Telemetría Anónima","icon":"satellite-dish","href":"/es/how_to_deploy/deploy_kodus/telemetry"},{"title":"Guía de solución de problemas","icon":"headset","href":"/es/how_to_deploy/deploy_kodus/troubleshooting"},{"title":"Actualización","icon":"arrow-up","href":"/es/how_to_deploy/deploy_kodus/updating"}]},{"group":"Desplegar con Kubernetes","pages":[{"title":"Kubernetes y OpenShift","icon":"dharmachakra","href":"/es/how_to_deploy/deploy_kodus/kubernetes"}]},{"group":"Configuración de Proveedores Git","pages":[{"group":"Github","icon":"github","pages":[{"title":"Crear una GitHub App","icon":"github","href":"/es/how_to_deploy/platforms/github/github_app"},{"title":"OAuth App de GitHub (Iniciar sesión con GitHub)","icon":"github","href":"/es/how_to_deploy/platforms/github/github_oauth"},{"title":"Crear un webhook","icon":"webhook","href":"/es/how_to_deploy/platforms/github/github_webhook"}]},{"group":"Gitlab","icon":"gitlab","pages":[{"title":"OAuth App de GitLab (Iniciar sesión con GitLab)","icon":"gitlab","href":"/es/how_to_deploy/platforms/gitlab/gitlab_oauth"},{"title":"Crear un webhook","icon":"webhook","href":"/es/how_to_deploy/platforms/gitlab/gitlab_webhook"}]},{"group":"Bitbucket","icon":"bitbucket","pages":[{"title":"Crear un webhook","icon":"webhook","href":"/es/how_to_deploy/platforms/bitbucket/bitbucket_webhook"}]},{"group":"Azure DevOps","icon":"microsoft","pages":[{"title":"Crear un webhook","icon":"webhook","href":"/es/how_to_deploy/platforms/azure_devops/azdevops_webhook"}]},{"group":"Forgejo","icon":"/images/forgejo.svg","pages":[{"title":"Creando un Webhook","icon":"webhook","href":"/es/how_to_deploy/platforms/forgejo/forgejo_webhook"}]}]}]},{"tab":"Base de Conocimiento","icon":"book-open","pages":[{"title":"Base de Conocimiento","href":"/es/knowledge_base/introduction"}]},{"tab":"Recetario","icon":"fire","pages":[{"title":"Recetario","href":"/es/cookbook/custom-plugin-install"}]},{"tab":"Changelog","icon":"newspaper","pages":[{"title":"Changelog","href":"/changelog"}]}]},{"language":"pt-BR","pages":[{"title":"pt-BR","href":"/pt-BR/how_to_deploy/deploy_kodus/analytics_worker"}]},{"language":"ja","pages":[{"title":"ja","href":"/ja/how_to_deploy/deploy_kodus/analytics_worker"}]},{"language":"zh","pages":[{"title":"zh","href":"/zh/how_to_deploy/deploy_kodus/analytics_worker"}]}]},"basePath":"","title":"Analytics Worker - Kodus","buildId":"dpl_9VVk5y1P8k1ATeJguVngy9Q3cmbD","deploymentId":"dpl_9VVk5y1P8k1ATeJguVngy9Q3cmbD","dynamics":[],"chunks":[]}