Ir al contenido

Elasticsearch

El destino Elasticsearch envía los puntos fechados de ghchronicle a Elasticsearch u OpenSearch en bloque, un documento por punto.

sinks:
elasticsearch:
url: http://elasticsearch:9200
prefix: ghchronicle
api_key: ${ES_API_KEY} # o username y password
batch: 1000

La API _bulk, que comparten Elasticsearch y OpenSearch, así que el mismo destino sirve a ambos, y a Kibana o a los dashboards de OpenSearch encima de cualquiera de los dos.

api_key: ${ES_API_KEY}

Se envía como Authorization: ApiKey.

No las dos. Configurar una clave de API junto a un usuario falla la validación al arrancar con sinks.elasticsearch: set either api_key or username and password, not both.

Un índice por medida, llamado <prefijo>-<medida>: ghchronicle-gh_repo, ghchronicle-gh_traffic.

Un documento por punto, con la hora como @timestamp en RFC 3339, measurement, y cada etiqueta y cada campo como clave de primer nivel, para que no haya que desanidar nada antes de poder filtrar por ello.

{
"@timestamp": "2026-09-07T00:00:00Z",
"measurement": "gh_traffic",
"owner": "acme",
"repo": "telemetry",
"full_name": "acme/telemetry",
"kind": "views",
"count": 220,
"uniques": 131
}

Por qué aquí también converge volver a recoger

Sección titulada «Por qué aquí también converge volver a recoger»

El id del documento es el SHA-256 de la medida, las etiquetas que tienen valor y la marca de tiempo, y la acción es index y no create. Así que escribir la misma ventana de tráfico de catorce días cada seis horas reemplaza catorce documentos en vez de añadir otros catorce, que es la misma convergencia que InfluxDB da de balde.

El destino no crea plantilla de índice. El mapping dinámico da a cada campo de texto un subcampo .keyword, que es sobre lo que agrega el dashboard.

Si quieres mappings explícitos, crea las plantillas de índice antes de la primera escritura. Nada del destino depende de ellas; solo la elección de .keyword en los paneles. -migrate lee el mapping antes de preguntar de quién son las filas de un índice, así que una plantilla que mapea las cadenas como keyword, sin subcampo .keyword, se lee del propio campo.

dashboards/ghchronicle-elasticsearch.json tiene los mismos 154 paneles que el de InfluxDB, como filtros Lucene y agregaciones sobre un solo datasource apuntando a <prefijo>-*, porque cada objetivo nombra su propio índice en su consulta.

Pon el campo de tiempo del datasource a @timestamp. Una tabla por elemento allí son los documentos más nuevos en sí, o el más nuevo de cada elemento cuando un elemento tiene varios; todo lo demás es una agregación por cubos. OpenSearch funciona con el mismo plugin.

Hay dos cosas que una consulta no puede hacer allí, y los paneles que las necesitan lo dicen. No puede unir dos índices, así que Work elsewhere no tiene columna Stars y el perfil de comunidad conserva la bandera de plantilla de issue de la API en vez del número de plantillas. Y no puede preguntar por una ventana mientras lee otra: el Overview y Every repository, ever cuentan un repositorio archivado que el filtro por omisión aparta por sus documentos de los últimos siete días, donde los almacenes SQL preguntan si el colector lo sigue escribiendo, así que un rango que terminó hace más de una semana deja fuera esos repositorios.

Cuando una versión cambia aquello por lo que se identifican los documentos de una medida, -migrate encuentra los documentos de la forma antigua contando los que llevan la etiqueta antigua, y aplicar el cambio aparta el índice en tres pasos. Medido contra Elasticsearch 9.5.3:

  1. El índice deja de aceptar escrituras, con PUT <índice>/_block/write.
  2. Se clona a <índice>-<instante>, el instante en UTC y en minúsculas, como exige el nombre de un índice, por ejemplo ghchronicle-gh_discussion_comment-20261001t091004, y el clon tiene que tener tantos documentos como el índice antes de que ocurra nada más.
  3. Se borra el índice, y la siguiente escritura del destino lo crea de nuevo, con un mapping propio.

Antes de aplicar el cambio, el plan pregunta de quién son las filas del índice y a qué repositorios pertenecen, con una agregación terms sobre el campo que el mapping deje agregar: el subcampo .keyword que da el mapping dinámico a una cadena, o el propio campo donde una plantilla lo mapea como keyword. Los buckets tienen que sumar todos los documentos que tienen el campo, o la respuesta no se acepta: medido en 9.5.3, una agregación sobre user.keyword en un índice cuya plantilla mapeaba user como keyword respondió sin buckets y sin error, lo que se leía como un índice sin filas de nadie más, y un valor que pasa del ignore_above del subcampo tampoco está en ningún bucket. Un documento sin el campo es una fila que no nombra a nadie, y el plan lo dice así.

Un paso que falla antes del borrado vuelve a quitar el bloqueo de escritura, así que un clúster que rechazó el clon sigue aceptando las escrituras del destino, y el cambio sigue pendiente con la razón del clúster. Un borrado que falla se vuelve a mirar antes de deshacer nada: medido a través de un proxy que respondió 502 a un borrado que el clúster llevó a cabo, el índice ya no estaba, así que el clon, la única copia de sus documentos, se conserva y el cambio se registra como aplicado; solo a un índice que sigue ahí se le quita el bloqueo y se le borra el clon. La clave de API necesita los privilegios manage y delete_index sobre los índices del prefijo; una clave que solo puede escribir se rechaza así.

El clon conserva el bloqueo de escritura, y ghchronicle lo borra cuando lleva 24 horas guardado: tras una pasada del servicio, en el siguiente arranque de cualquier ejecución o en el siguiente -migrate -yes. Hasta entonces, deshacer el cambio es borrar el índice nuevo y clonar la copia de vuelta con su nombre. Toda consulta del dashboard que se distribuye nombra su índice entero, _index:ghchronicle-gh_discussion_comment, así que ningún panel lee el clon: la consulta de un panel sobre ghchronicle-* contó el único documento nuevo y no los tres del clon. Una data view de Kibana sobre el mismo patrón sin ese filtro sí lo lee, durante el día que se guarda.

  • Elegir almacén compara Elasticsearch con los demás, y lleva el registro de escrituras que todos comparten.
  • Los dashboards dice cuál de los cinco se dibuja contra cada almacén, y en qué se convierte un panel que un almacén no puede responder.