Saltar al contenido
weekly10 de mayo de 2026·5 min

La semana en la que Chordna empezó a alimentarse sola

Chordna monta un consumer de trending que se autoalimenta vía Claude Max OAuth, Sofi por fin manda los resúmenes que tenía que mandar, y de paso descubrimos que los recordatorios recurrentes llevaban roto más tiempo del que nos gustaría admitir.

Hay semanas de fontanería y semanas en las que algo hace clic. Esta fue de las segundas: Chordna pasó de ser una enciclopedia musical que esperaba a que alguien le diera de comer, a un sistema que se busca la vida y se mete trending en la cola él solito. Y Sofi, mientras tanto, dejó de tener vergüenza los fines de semana.

Chordna: el consumer que se alimenta a sí mismo

El problema era aburrido pero real: el analysis_queue de Chordna dependía de que un humano (o un cron muy tonto) decidiera qué canciones analizar. Eso funciona los tres primeros días y luego se convierte en deuda. La FEAT-007 y sus hijas (007B, 007C, 007D, 007E) son básicamente la historia de cómo destripar esa dependencia.

Primero, FEAT-007 montó el auto-trending feeder: un proceso que mete candidatos en la cola sin intervención. Hasta ahí, normal. Lo interesante llegó con FEAT-007B, que conecta un consumer de trending vía Claude Max OAuth. Sí, OAuth de Claude Max, no API key — esto importa porque significa que el coste por análisis es predecible (cubierto por la suscripción) en lugar de un contador girando con cada llamada. Hay un matiz: Anthropic lleva desde abril prohibiendo OAuth Max + tools en herramientas terceras, así que este patrón solo aguanta porque corre desde nuestro propio entorno, no desde un gateway. Si algún día cambia la política, toca rehacer. Lo asumimos.

El pequeño drama técnico vino con el índice de Firestore: el query nuevo necesitaba un compuesto sobre status + source + priority + createdAt, y hasta que no se desplegó, el consumer no servía para nada. Es de esos bugs que no son bug — el código está perfecto, simplemente Firestore te exige el índice y hasta que no lo tiene, devuelve nada con cara de póker.

FEAT-007C cerró el bucle: el propio consumer de Claude se autoalimenta, metiendo 10 trending nuevos cada ejecución. FEAT-007D corrigió un detalle de producto que casi pasa desapercibido — seedTrending ahora hace fetch ancho pero inserta capado, así que aunque la fuente devuelva 80 candidatos, solo metemos los N que tienen sentido procesar. Y FEAT-007E añadió geo-charts como fuente secundaria, porque depender de una sola fuente de trending es la receta clásica para descubrir que tu feed son tres reggaetones en bucle.

De paso, FEAT-023 arregló integridad de datos en álbumes y creó la colección albums/{albumId} con su backfill productivo el 9 de mayo. No es glamuroso, pero hasta que no tienes una entidad limpia de álbum, las relaciones canción↔álbum son un desastre eventual. Y la FEAT-021+022 del 7 de mayo dejaron resuelto el caso de "álbum original" (cuando una canción aparece en compilaciones, EPs, deluxe, etc., ¿cuál es el canónico?) y una lista de "appearances" para mostrar todos los sitios donde aparece. Ese tipo de cosas son las que separan una base de datos musical de una enciclopedia musical.

Detalle de fontanería que vale la pena: el cron de deploy del frontend se movió a las 07:30 para no chocar con el cron-blog de las 07:00. Parece tontería hasta que se te solapan dos builds en una máquina pequeña y se cae todo.

Sofi: por fin los fines de semana cuentan

Sofi acumuló esta semana esa clase de fixes que duelen cuando los descubres. HF1+HF2+HF3 sobre el resumen semanal y los recordatorios recurrentes: literalmente, había recordatorios que se suponía debían dispararse cada semana y no lo hacían. El resumen semanal tampoco terminaba de cuadrar. Tres hotfixes seguidos para dejarlo decente, lo cual es un buen recordatorio (irónicamente) de que los crons que "funcionan" hay que mirarlos de vez en cuando.

Otro fix sutil: el menú de Sofi devolvía la consulta mal en fin de semana — colegio cerrado, por supuesto, pero la lógica trataba sábado/domingo como si nada. Pequeño, embarazoso, arreglado. Y los resúmenes diarios ahora se envían todos los días sin excepción, en lugar de saltarse fines de semana "por silenciosos". La filosofía cambió: mejor un resumen tranquilo ("hoy no hay nada") que un silencio que el usuario interpreta como bug.

La pieza grande fue FEAT-013: Racionalización Gemini API — arquitectura heurística-first. En cristiano: antes, Sofi tiraba de Gemini para tareas que se resolvían perfectamente con reglas. Ahora la heurística decide primero y Gemini entra solo cuando aporta. El ahorro de coste y latencia es notable, y de paso quitamos el thinking mode de los resúmenes matutinos y vespertinos (era caro y no aportaba — pensar mucho un "buenos días, hoy toca dentista" es de hipster).

Y FEAT-012: Langfuse observability entró integrado para tracear las llamadas a Gemini. Con un asterisco doloroso: la decisión global del 17 de mayo fue descartar Langfuse por completo en todo el portfolio, así que este wrapper queda como no-op pendiente de eliminar. Es un buen ejemplo de algo que es producto real durante una semana y deuda técnica la siguiente. Pasa.

Lo que queda en el aire

Dos cosas que se ven en el commit log y vale la pena nombrar:

  • Chordna sigue dependiendo de Claude Max OAuth para el consumer. Funciona, es barato, y mientras no cambie la política de Anthropic, seguirá funcionando. El día que cambie, hay que tener plan B listo — no nos vamos a engañar pretendiendo que lo tenemos.
  • Sofi acaba de quitar Langfuse de su pipeline antes incluso de explotarlo del todo. Es la decisión correcta a nivel portfolio (no había usuarios suficientes para justificar el stack), pero deja un wrapper huérfano que toca limpiar.

Semana de menos commits que la anterior, más decisiones que código. A veces el progreso se ve mejor cuando dejas de añadir cosas y empiezas a quitarlas.