Resolución de problemas
Cosas que parecen errores y no lo son
Sección titulada «Cosas que parecen errores y no lo son»not available (403) o (404). La función está apagada en ese repositorio,
o el token no la ve. Dependabot, code scanning, las discusiones y el grafo de
dependencias responden así cuando están desactivados. El colector anota el hecho
y sigue: un repositorio con una función apagada no debe detener la pasada de los
otros cuarenta.
Si son todos los repositorios y no uno, es el token. El tráfico necesita
acceso de escritura y, en un token fine-grained, el permiso de repositorio
Administration (lectura); las alertas necesitan security_events. Ver
el token.
Una función encendida y nada recogido de ella. Code scanning activado esta mañana, Dependabot encendido, un foro abierto: el colector preguntó antes de que lo hicieras, le dijeron que no, y recuerda ese rechazo un día en vez de pagarlo en cada pasada. Se nota como muy tarde al día siguiente, también tras un reinicio; borrar el fichero de caché junto al fichero de estado vuelve a preguntar en el acto. Ver un rechazo también se recuerda.
still being computed by GitHub (202). GitHub calcula los endpoints
stats/* de forma asíncrona y responde 202 con cuerpo vacío mientras trabaja.
La siguiente pasada suele conseguir los números.
Dos de ellos no lo hacen nunca. En una cuenta personal
stats/code_frequency y stats/contributors devuelven 202 con cuerpo vacío
indefinidamente, que es por lo que este proyecto no los llama: las líneas
añadidas y quitadas salen del colector de commits.
pagination is limited for this resource (422). El final de un feed de
actividad, no un fallo. GitHub sirve tres páginas del feed de eventos y rechaza
la cuarta.
Un repositorio sin tráfico mostrando una ventana que terminó hace semanas. GitHub sigue devolviendo los últimos catorce días que tuvieron datos, no los últimos catorce días. El colector anota lo que le dicen.
cache file not read, the first pass of each family pays in full. El
fichero de caché que hay junto al fichero de estado quedó cortado, dañado o
escrito en otro formato, así que no se lee en absoluto, y el siguiente guardado
lo sobrescribe. Cuesta una pasada de cada familia a precio completo y no pierde
nada; ver la caché que hay a su
lado.
which repositories moved could not be asked, reading those it did not answer for. La consulta que dice a commits, issues e issueevents qué
repositorios leer falló, o respondió por algunos de ellos. Cada repositorio del
que no dijo nada se lee como si no se hubiera preguntado, así que no se pierde
nada y la pasada cuesta lo que costaba antes de que existiera la consulta; ver
preguntar primero qué se movió.
outbound search read fewer items than it counts, GitHub serves a thousand at most. GitHub sirve mil resultados de una búsqueda y ni uno más, y la cuenta
tiene más que eso en uno de los estados que busca outbound, las pull requests
fusionadas por ejemplo. Se quedan los mil que se movieron más recientemente, y
la línea se dice una vez por recuento; ver qué alcanza que una pasada
no.
NOTICE: column ... already exists, skipping de psql. Reproducir el fichero
del destino SQL en una base de datos que ya tiene sus tablas. El fichero
declara cada tabla y cada columna de campo que escribe, porque no puede
preguntar cuáles existen, y PostgreSQL lo dice por cada una que ya está, con un
relation ... already exists para la tabla. No ha fallado nada.
Una familia que no aparece nunca en el log. Aún no le toca. Con una cadencia
de doce horas, medio día de logs puede legítimamente no mencionar nunca
stats. Una familia de seis horas o más también puede tocarle y estar esperando
su turno detrás de otra, y el log la nombra bajo waiting en
slow families due together take turns; ver
las familias lentas se turnan.
Cosas que sí son errores
Sección titulada «Cosas que sí son errores»github.token is empty and GITHUB_TOKEN is unset. Exactamente lo que dice.
every.families.<name>: unknown collector. El nombre no es una familia. El
mensaje lista las treinta y cuatro que existen, en un paréntesis tras los dos
puntos.
groups: is empty. groups: [] no recogería absolutamente nada. Omite la
clave para recogerlo todo, que es lo que significa cuando no está.
groups[N]: "<name>" is not a group. El nombre no es un grupo. El mensaje
lista los que existen, y ghchronicle -groups imprime cada uno con sus familias.
groups[N]: "<name>" is a family, not a group. Familias y grupos son
sustantivos en minúscula de la misma tabla, así que este es fácil de encontrar.
El mensaje nombra el grupo en el que está la familia, que probablemente es lo que
querías, y apunta a every.families.<name>, que es donde vive la cadencia de una
sola familia.
sinks: enable at least one of .... Una ejecución que recoge y tira es casi
nunca lo que alguien quiso. -card-only es la excepción y no necesita ningún
destino.
prometheus exporter: listen tcp :9605: bind: address already in use. Se
informa al arrancar en vez de quedar sepultado en una goroutine, para que un
choque de
puerto no te deje con un colector corriendo y un exportador ausente en silencio.
influx write: 400. Casi siempre una colisión de tipo de columna. InfluxDB
fija una columna como etiqueta o como campo la primera vez que la ve y rechaza
las escrituras posteriores que no coincidan. Si un colector cambió de qué tipo
es un nombre, hay que borrar la tabla: DELETE /api/v3/configure/table.
family failed everywhere, not marking it as run. Fallaron todos los
repositorios en una familia, así que se reintentará en vez de darse por hecha.
Que falle un repositorio es normal; que fallen todos es el token, la red o una
caída.
collector failed que nombra un 500, un 502 Bad Gateway, un 503 o un
504 Gateway Timeout. GitHub no terminó la respuesta a una petición, en su
pasarela o en la aplicación, o no la terminó el almacenamiento del que se lee
el log de un job. El cliente pregunta una vez más dos segundos después y no dice
nada de ello, así que una línea como esta es una petición que falló dos veces, y
la siguiente pasada vuelve a preguntar. Una consulta GraphQL se vuelve a
preguntar del mismo modo, salvo por una respuesta: un 502 o un 504 que tardó
los diez segundos de GitHub en volver es una consulta demasiado grande, que los
colectores que tienen una página más pequeña vuelven a preguntar con ella. Una
línea que dice que la consulta es demasiado grande para una sola petición es
una que agotó el tiempo incluso con la página más pequeña, o en un recorrido
sin página más pequeña que pedir. Lo leído antes se escribe, un relleno no
anota ese repositorio como recorrido, y la pasada siguiente lo vuelve a leer.
state not saved o cache file not saved. El usuario con el que corre el
colector no pudo poner el fichero en su sitio. Cada uno de los dos se escribe
con un nombre temporal en el directorio que nombra el fichero de estado y
después se renombra a su sitio, así que o no se puede escribir en ese
directorio, o no existe y no se puede crear, o el propio fichero no se puede
sustituir con un renombrado. Nada de lo que aprende una pasada sobrevive
entonces a un reinicio: el siguiente arranque recoge todas las familias y vuelve
a recorrer la lista de estrellas, el historial entero de estrellas y las pull
requests en coautoría. En un contenedor es un directorio del anfitrión montado
sin entregárselo al uid 65532, un volumen nuevo montado en otro sitio que no sea
/var/lib/ghchronicle, o cualquier volumen nuevo con una imagen anterior a la
2.6.1, ninguno de ellos de ese uid, o un fichero de estado montado solo, sobre
el que no se puede renombrar; ver qué tiene que ser
escribible.
the state file ... cannot be read o does not parse, y la ejecución se
detiene. El fichero de estado está ahí y esta ejecución no pudo leerlo, o no
está entero. Una ejecución que escribe en los almacenes no lo toma por uno
nuevo, lo que olvidaría las relecturas que una migración aún debe y pondría un
fichero nuevo en su lugar en su primer guardado. Un fichero que dejó root, tras
un -migrate -yes o un relleno lanzado con sudo, es la causa habitual:
devuélveselo con chown al usuario con el que corre el colector. Si se aparta
en su lugar, la siguiente ejecución empieza con uno nuevo, y lo que registraba,
entre ello una relectura aún debida, se pierde; ver el fichero de
estado.
rate limit reserve reached, family skipped. Una vez está bien. En cada
pasada significa que las cadencias son demasiado rápidas para el número de
repositorios. Si el cubo que se queda corto es core, alarga artifacts y
después actions; si es graphql, issues, issueevents y commits. Ver
qué crece con la actividad, no con el
tamaño.
refill owed: a store a migration cleared does not hold that history yet.
Una migración despejó la medida que se nombra en ese almacén y volver a leer su
historial de GitHub no terminó: se paró la ejecución, un almacén rechazó una
escritura o GitHub no respondió. Ahora el almacén parece uno que nunca guardó
la forma antigua, así que solo lo sabe el fichero de estado. Bajo
migrate: warn un arranque lo dice y hace su pasada; -migrate -yes, que la
línea nombra, lo vuelve a leer desde donde se paró, y también cualquier
arranque bajo migrate: auto. Ver volver a leer el
historial.
Los datos parecen mal
Sección titulada «Los datos parecen mal»reconciled en WARN, con not_served. Tras volver a leer una medida
despejada, ghchronicle comparó la copia de las filas antiguas con la tabla y
encontró elementos que GitHub ya no sirve: un repositorio borrado o que ya no
se cubre, un comentario borrado, una alerta cuya función se apagó. first
nombra unos pocos, y only_in es la copia que aún los guarda, hasta que se
purga: un día después de la migración las de PostgreSQL y Elasticsearch, y
cuando diga el calendario del servidor la de InfluxDB 3, 72 horas por omisión,
o nunca en un servidor anterior a la 3.2. Traspasarlos se hace a mano, desde esa copia, mientras está.
Un número es múltiplo del número de pasadas. Algo que es una instantánea se está sumando en el tiempo. Los referrers, las rutas, las etiquetas y los hitos son instantáneas de una ventana sin fecha propia; se sellan al inicio del día UTC para que las pasadas de un día reescriban una fila, y el dashboard toma la más reciente y no la suma.
La mediana de tiempo hasta la revisión de otra persona dice No data. El panel lee
seconds_to_first_human_review, que deja fuera a los bots de revisión y las
respuestas del propio autor; en una cuenta donde nadie más revisa, ninguna pull
request lo lleva y la tarjeta está honestamente vacía. No significa que no se
haya revisado nada. La velocidad de los bots
está en la tabla Reviewers, donde cada uno va marcado como bot: medido, nueve
de cada diez pull requests tuvieron una revisión de un bot en menos de un
minuto.
Los clones son enormes comparados con las visitas. La integración continua
clona un repositorio miles de veces por cada visita humana. Un repositorio
medido aquí tuvo más de cien clones por cada visita. clones no cuenta
personas.
open_issues no cuadra con el número de issues. Ese campo es de GitHub, y
GitHub cuenta las pull requests como issues dentro. La medida gh_issue es la
que cuenta issues.
El almacenamiento de artefactos parece pequeño. Compara walked con count
en gh_artifact_total. Cuando no coinciden, el tamaño vivo es un suelo: el
repositorio tiene más artefactos de los que recorrió el tope de páginas, o una
página del listado falló en esa pasada y la fila se escribió con las páginas
anteriores. También puede salir más pequeño de lo esperado por una segunda
razón: count es el total de GitHub e incluye los artefactos que ya ha
caducado, mientras que el tamaño es solo sobre los vivos, que son los que cuenta
live_count.
Un panel responde con un error de esquema en vez de decir No data. InfluxDB 3
crea una columna la primera vez que una fila la trae, así que una consulta que
nombra una que ninguna fila ha escrito falla al planificarse. Una versión que
añade un campo le hace eso a una base ya existente hasta que la familia que lo
escribe hace una pasada: gh_fork.seconds_to_push y
gh_artifact_total.live_count fueron dos, que nombran los paneles Forks y
“Artifact storage counted”, y la familia forks corre cada doce horas. Una
versión que añade una medida con la que un panel hace un join le hace lo mismo
al panel entero, también en PostgreSQL, donde lo que falta es la tabla y no la
columna: la tabla “Work elsewhere” hace un join con gh_upstream_repo para las
estrellas de cada repositorio, y hasta que la primera pasada de outbound de la
versión nueva la escribe, que es dentro de una hora, los dos almacenes rechazan
la tabla en vez de dejar vacía su columna Stars. Espera esa pasada o publica
los dashboards después. Un -once no la adelanta: corre solo las familias a
las que les toca, y a outbound no le toca hasta una hora después de su última
pasada. Las demás columnas que pueden
faltar están en
Columnas que solo existen una vez escritas.
La gráfica de tráfico solo llega catorce días atrás. Eso es una primera pasada. La ventana se reescribe día a día en cada pasada, así que la serie se extiende conforme el colector sigue corriendo. No se puede rellenar: GitHub nunca guardó nada más viejo.
Un panel dice “Query would scan 10000 Parquet files”. InfluxDB 3 Core
escribe un fichero por partición y por petición de escritura, y no los compacta
nunca, así que un almacén alimentado por una versión de esta herramienta
anterior al registro de escrituras guarda sus filas en muchos más ficheros de
los que necesita. Ensanchar el intervalo del panel no ayuda: el límite cuenta
los ficheros que abre el planificador, antes de cualquier agregación. Lo que
ayuda es el registro, que viene encendido y detiene el crecimiento, y después
una de tres cosas para lo ya acumulado: subir --query-file-limit en el
servidor, reescribir las tablas afectadas, o pasar a InfluxDB 3 Enterprise, que
compacta por su cuenta y es gratis para uso doméstico. Ver
solo se escribe lo que ha cambiado.
Un panel de Prometheus muestra una línea plana. Eso es el almacén, no los datos. El exportador sirve valores actuales, así que la ventana de tráfico de catorce días se colapsa a su día más reciente y la historia de estrellas al total actual. Ver la fecha del punto.
¿Por qué no se escribe nada?
Sección titulada «¿Por qué no se escribe nada?»Ejecuta una pasada en primer plano y lee lo que dice. Después comprueba, en orden:
- que
-listimprime los repositorios que esperas, - que el log de la pasada dice
written, - que el destino es alcanzable.
ghchronicle -config config.yaml -list # los repositorios, y cuáles quedan aparteghchronicle -config config.yaml -once # una pasada en primer plano, y salirjournalctl -u ghchronicle -f # bajo systemddebug añade esto a eso y nada más: el tamaño del libro de escrituras al
arrancar, un primer arranque sin fichero de caché, un arranque que vuelve a
listar jobs porque un almacén no lleva registro, las familias de cuenta
saltadas por falta de targets.user, las entradas que un destino dejó fuera
por viejas, una pasada solo de tarjeta que deja en paz el fichero de estado,
cada guardado del fichero de caché, las migraciones que un arranque encuentra
innecesarias o ya aplicadas, las anotadas o congeladas que el primer arranque
dijo en INFO, y cada copia que apartó una migración y que el fichero de
estado olvida porque el almacén la purga o la guarda para siempre. No hay
registro por petición en ningún nivel. Ver depuración.
log: level: debugUna familia a la que aún no le toca sencillamente no aparece.
¿Por qué Loki descarta entradas?
Sección titulada «¿Por qué Loki descarta entradas?»Busca la línea de depuración que las cuenta. Loki rechaza una entrada que esté
más atrasada que su ventana de desorden respecto a la entrada más nueva que ya
hay en ese stream, la mitad del max_chunk_age del ingester y así una hora por
omisión, así que el destino deja fuera las más viejas en vez de perder el envío
entero. Sube max_age solo junto al propio max_chunk_age de Loki. Ver
Loki.
Publicar el dashboard
Sección titulada «Publicar el dashboard»Permissions needed: datasources:create. El token publica dashboards y no
puede crear datasources. Un Editor puede lo primero y no lo segundo, así que
dale ese permiso a la cuenta de servicio, hazla Admin, o deja que adopte un
datasource creado por ti nombrándolo en grafana.datasource.uid, que solo lee.
Corregir un datasource que ya está pide datasources:write en su lugar, con
las mismas salidas. Eso detiene la ejecución para el datasource del almacén,
que leen todos los paneles. Para el de Loki es solo un aviso, más abajo.
datasource ... does not answer: connection refused. Grafana llegó a la
dirección y no había nadie escuchando, que casi siempre significa que la
dirección es la buena para el colector y la mala para Grafana. Un colector en
el anfitrión escribe a un puerto publicado; Grafana en un contenedor llega al
mismo almacén por su nombre en la red de contenedores, y 127.0.0.1 allí es el
contenedor. Pon en grafana.datasource.url la dirección que usaría Grafana. La
ejecución se niega en vez de publicar, porque un dashboard contra un datasource
inalcanzable no dibuja nada y no dice por qué.
asking datasource ... whether it answers: ... datasources:query. El token
no puede consultar el datasource, que no es lo mismo que un datasource que no
llega a su almacén, y la dirección no es lo que hay que cambiar. Medido en
Grafana 13, una cuenta de servicio sin rol recibe esto y un Editor no, así que
dale el rol de Editor.
Invalid API key. El token llegó a Grafana como los caracteres
${GRAFANA_TOKEN} y no como un token, lo que significa que la variable no está
donde corre el colector. En una unidad de systemd eso es un EnvironmentFile
que la unidad no lee, o una variable nombrada en el fichero y no exportada.
El datasource está y no tiene contraseña. Solo se envía una contraseña que
escriba el propio DSN. Una que pgx encontrara en PGPASSWORD o en un .pgpass
de la máquina que publicó se nombra en una línea y se queda ahí, porque un
Grafana es compartido y una credencial que la configuración nunca mencionó no
es cosa de copiar dentro.
the dsn asks for sslmode=prefer and Grafana's datasource has no such mode. Lo que hace libpq por omisión es intentar TLS y seguir sin él, y el
datasource o exige o rechaza. Se le puso disable; pon
grafana.datasource.sslmode en require, verify-ca o verify-full si eso
no encaja con tu servidor.
Dos dashboards, y el que miras deja de cambiar. El generado tiene su propio
uid y cada publicación lo sobreescribe, así que esto solo pasa cuando el tuyo
vive en otro sitio: importado como nuevo, o renombrado a mano. Nombra el que
lees en grafana.dashboard_uid.
... is still in Grafana and no ... sink is configured here. Algo que esto
creó está bajo un uid al que ya nadie escribe, que es lo que deja atrás cambiar
de almacén. Es un aviso y no se tocó nada; bórralo en Grafana cuando hayas
terminado con él.
no sink this builds a dashboard for is configured. Hay dashboards para
cinco almacenes y el sink que tienes no es uno de ellos. Un sink que reenvía no
tiene dashboard propio porque el dashboard pertenece al destino, y file,
stdout y loki no son almacenes de métricas.
warning: the Loki datasource ghchronicle-loki could not be set up. El
token no puede crear el datasource de Loki del que lee el panel de la salida del
trabajo fallido, y la línea nombra el permiso que le falta: datasources:create
para un Editor, porque el datasource aún no está. Nada más espera por él: ese
único panel queda como la nota que llevan los ficheros exportados, y los
dashboards se publican siempre que se pueda el datasource del propio almacén.
Nombra en grafana.datasource.loki_uid un datasource de Loki que Grafana ya
tenga, o concede el permiso. La línea enumera los datasources de Loki que tiene Grafana,
con sus direcciones, porque el que hay que nombrar suele estar ya ahí bajo una
dirección a la que el colector no envía, como el nombre de Loki en la red de
contenedores de Grafana. La 2.4.0 y la 2.5.0 detenían aquí toda la
publicación, con the Loki datasource: writing datasource ghchronicle-loki, y
loki_uid también lo arregla en ellas.
warning: the Loki datasource ghchronicle-loki is used as Grafana has it.
Lo creó una ejecución anterior con un token que podía escribir datasources, y
este token no puede reescribirlo: la línea nombra datasources:write. Un sink
con tenant_id pide esa reescritura en cada arranque, porque el tenant es un
secreto que Grafana nunca devuelve para comparar, y también la pide un
datasource cuya dirección se cambió a mano. El panel lo lee tal cual, así que
no se pierde nada salvo que el sink se haya movido desde entonces. Concede al
token datasources:write para mantener su dirección y su tenant al día con el
sink, o pon grafana.datasource.loki_uid en ghchronicle-loki para leerlo
sin intentarlo.
datasource ... (loki) adopted. Grafana ya tenía un datasource de Loki en
la dirección de la que sale el extremo de envío del sink, así que el panel lee
ese y no se creó un segundo. Adoptar solo lee, así que un token que no puede
crear datasources llega hasta aquí. Un sink con tenant_id nunca se empareja
así: el tenant viaja en un secreto que Grafana nunca devuelve, así que nada
puede saber si el datasource de esa dirección lee el mismo tenant, y se crea
uno.
El panel de la salida del trabajo fallido sigue siendo una nota. Ese panel
pasa a ser las líneas cuando hay un sink de Loki cuya dirección termina en
/loki/api/v1/push, que es lo que dice dónde está el extremo de consulta. Un
sink que escriba en otro sitio lo dice y deja el panel como está; nombra un
datasource de Loki en grafana.datasource.loki_uid. Un token que no puede
crear el datasource también lo deja así, con el aviso de arriba.
No se publicó nada y no falló nada. publish_on_start está apagado salvo
que lo enciendas, y se salta en -once, -backfill y -card, porque
encenderlo en una unidad de systemd no quería decir reescribir el dashboard en
cada ejecución de una tarjeta programada.
El colector arrancó y el dashboard no apareció. Una publicación que falla al arrancar avisa y la pasada sigue. Las métricas de una hora sin recoger no se recuperan y un dashboard publicado al siguiente arranque sí, así que el sitio donde mirar es la línea del log.
Quitar cosas
Sección titulada «Quitar cosas»-uninstall imprimió una lista y no quitó nada. Eso es lo que hace por
omisión. Añade -yes.
El datasource sobrevivió al uninstall. Uno nombrado en
grafana.datasource.uid se adopta, no se crea, así que era de otro antes de
que esto corriera y sigue siéndolo.
unknown -uninstall target. Se rechaza la lista entera en vez de la parte
que se entendió, así que una errata no quita nada. Los objetivos son
dashboard, data, state y all.
Las filas siguen en la base después de -uninstall data. Tres almacenes no
se pueden vaciar desde aquí y lo dicen: Graphite no tiene borrado, el sink de
Prometheus se raspaba en vez de recibir escrituras, y el fichero del sink SQL
se va pero las filas que ya cargaste de ahí a una base de verdad las cargaste
tú.
Tablas o índices llamados gh_...-20261001T091004. Una migración apartó
las filas antiguas de la medida con ese nombre, la medida, un guion y el
instante en UTC: la tabla renombrada de PostgreSQL, el clon de Elasticsearch,
allí en minúsculas, y el nombre que InfluxDB 3 da a una tabla que borró.
Ninguno de los paneles que se distribuyen lee ninguna. ghchronicle purga las de
PostgreSQL y Elasticsearch cuando llevan 24 horas guardadas, e InfluxDB 3 purga
las suyas con su propio calendario, 72 horas después del borrado por omisión,
salvo una que borró una versión anterior a la 3.2, que no se purga nunca, ni
siquiera después de actualizar (ver antes de la 3.2 la copia se
queda);
-migrate las lista bajo su almacén como kept aside. -uninstall data quita
las de PostgreSQL y Elasticsearch con todo lo demás, y deja fuera las de
InfluxDB 3 con una nota que dice cuáles se quedan, porque el servidor rechaza el
borrado de una tabla que ya ha borrado, o, antes de la 3.2, la renombra otra
vez.
Tras una actualización
Sección titulada «Tras una actualización»migration pending, en cada arranque. Un almacén guarda filas de una medida
con una forma que esta versión ya no escribe, y este arranque no lo puso al
día. not_applied dice por qué: migrate: warn, o un motivo por el que el
cambio necesita la palabra de alguien, como un InfluxDB 2, cuya única vía es un
borrado definitivo, un fichero SQL, un Graphite o un Telegraf, donde ghchronicle
no aparta nada, filas de cuentas que esta configuración no recoge, filas que
volver a leer no traería de vuelta, o filas cuyas cuentas o repositorios no se
pudieron leer, lo que un InfluxDB 3 Core que pasa de su límite de ficheros por
consulta se niega a decir; o una ejecución de una sola vez sobre un fichero de
estado nuevo, cada ejecución de la Action sin uno restaurado, que no aplica
nada por su cuenta. plan y apply son las dos órdenes, y first, en el
servicio, dice que lo pares antes de la segunda. Se dice en cada arranque hasta
que el almacén se pone al día: mira
Migraciones.
applying a migration before the first sweep. No es un error. Con
migrate: auto el arranque encontró un cambio que puede aplicar sin perder
nada, y lo está aplicando: found es lo que guarda el almacén, action adónde
van las filas antiguas, y refill lo que se vuelve a leer de GitHub. Sale una
vez por almacén y cambio, seguido de refill starting, refill complete y
reconciled, y luego la primera pasada.
migration noted: nothing is changed o migration frozen. Tampoco son
errores. Una nota es un cambio que nada puede arreglar, como las filas de
gh_actions_cache_entry fechadas antes de la 2.6.0, y una medida congelada es
una que ya no escribe nada de lo que corre esta configuración. Cada una se dice
una vez en INFO y después en DEBUG.
migration check failed: the store did not answer. Al arrancar se preguntó
al almacén si guarda una forma antigua, y lo rechazó o no respondió en 30
segundos. No se anotó nada ni cambió nada; la pasada sigue, y el siguiente
arranque vuelve a preguntar.
migration failed. El almacén rechazó lo que aplicar le pidió, y el cambio
sigue pendiente; los demás almacenes siguieron adelante. err dice por qué, y
el motivo habitual es una credencial que puede escribir y no borrar: el token de
InfluxDB 3 tiene que poder borrar una tabla, y el error lleva el mismo borrado
como un curl para ejecutarlo a mano; el usuario de PostgreSQL tiene que ser
dueño de la tabla, como lo es cuando la creó su propio destino; una clave de
Elasticsearch necesita manage y delete_index sobre los índices de su
prefijo. PostgreSQL además se rinde tras tres esperas de 5 segundos cada una
detrás de una consulta que tiene la tabla, y una consulta larga de Grafana
puede serlo. Ejecuta la misma orden otra vez cuando esté arreglada la causa: lo
aplicado queda anotado y no se hace dos veces.
refill did not finish, and is still owed. Volver a leer lo despejado se
detuvo: se paró la ejecución, un almacén rechazó una escritura o GitHub no
respondió. resume dice cómo seguir. El recorrido guarda su punto de control
junto al fichero de estado, <nombre>-refill.json, y refill owed, en cosas
que sí son errores, es lo que dice de él un arranque
posterior.
the store may have been cleared, so the refill stays owed. Despejar el
almacén falló de una manera que no dice si se llevó a cabo: un 502 de un proxy,
un tiempo agotado, una conexión que se rompió después de que el almacén hiciera
lo que se le pidió. La relectura se anotó como debida antes de tocar el almacén
y sigue debiéndose, así que el historial se vuelve a leer ocurriera o no el
despeje; el cambio se vuelve a preguntar en el siguiente arranque. Como mucho
eso lee el historial una vez para nada.
the state file records a refill owed to ... where it no longer points.
Una migración despejó un almacén, la relectura no terminó, y el destino apunta
ahora a otro almacén. El registro se conserva, y la relectura se lee la próxima
vez que el destino apunte allí; hasta entonces nada la lee. -migrate la
muestra bajo el almacén como owed there.
not reconciled: the copy and the table could not be compared. El
historial se volvió a leer, y la copia de las filas antiguas no se pudo leer, o
ya tocaba purgarla. Lo que volvió está en la tabla; solo falta la lista de lo
que GitHub ya no sirve, y mientras la copia siga ahí se puede leer a mano.
set-aside copy not purged o set-aside copies not listed. Un día después
de que una migración la apartara, ghchronicle no pudo quitar la copia de
PostgreSQL ni borrar el clon de Elasticsearch, o no pudo preguntar al almacén
qué copias guarda. Lo vuelve a intentar tras cada pasada y en cada arranque;
aside nombra la copia, que también se puede quitar a mano. InfluxDB 3 purga
las suyas con su propio calendario, o, antes de la 3.2, nunca.
the cache file still claims what the cleared store held. Una migración no
pudo reescribir el fichero de caché para olvidar los rechazos, y las ejecuciones
de workflow ya escritas, de las familias que vuelve a leer, así que esas
familias pueden seguir saltándose lo que el almacén despejado ya no guarda. Con
el servicio parado, borrar <nombre>-cache.bin cuesta una pasada a precio
completo: la caché que hay a su
lado.
-migrate -yes responde process N (ghchronicle ..., service, since ...) holds ...-lock. El servicio, u otro -migrate -yes, tiene el fichero de
estado, y no se cambió nada. Páralo, o deja que termine, y ejecuta la orden otra
vez. En Docker, N es el proceso con el número que le da el contenedor del
propio servicio.
waiting for the process holding the state file to finish. El servicio se
arrancó mientras -migrate -yes corría sobre el mismo fichero de estado.
Espera a que termine y luego arranca sobre lo que dejó.
another ghchronicle service keeps the same state file. Se arrancó un
segundo servicio sobre un fichero de estado que ya tiene uno en marcha, y se
rechazó, porque dos servicios que guardan un mismo fichero de estado deshacen
las marcas del otro. Para uno, o da a cada uno su propio state_file.
the state file cannot be locked, so -migrate -yes cannot tell this service is running. El servicio no pudo crear ni abrir <nombre>-lock junto al
fichero de estado: el directorio no es escribible, o una ejecución como otro
usuario, casi siempre root, creó el fichero. El servicio corre sin el candado, y
entonces -migrate -yes se niega a correr, porque nada impediría que el
servicio arrancara por debajo de él a medias. Ejecútalo con el usuario del
servicio: tras una
actualización.
El PostgreSQL que conecta
Sección titulada «El PostgreSQL que conecta»could not reach its database. El sink conecta en la primera escritura y
no al arrancar, así que esto es la primera pasada y no la lectura de la
configuración. El DSN admite las dos formas que admite libpq, y el mensaje es
el del driver.
Falta una columna en vez de la fila. Un campo sin valor no ocupa celda: una cadena vacía se deja fuera, y un float que no es un número se guarda como NULL. La columna aparece la primera vez que un punto lleva algo para ella.
Un campo cambió de tipo y el insert falla. Una columna se crea con el tipo del primer valor visto y no se altera después, así que un campo que era un número y ahora es una cadena no tiene dónde ir. Renombra el campo, o tira la tabla, y la siguiente escritura del colector la declara otra vez. No hace falta reiniciar: el destino declara una tabla una vez por proceso, y el primer insert tras el borrado se rechaza porque la tabla no está, así que el destino olvida las tablas de ese lote, las declara de nuevo y reenvía el lote una vez.
Se rechazan las sentencias de gh_discussion_comment del fichero SQL. Con
there is no unique or exclusion constraint matching the ON CONFLICT specification, reproducido en una tabla que creó una versión anterior a la
2.6.1. Esa tabla conserva is_answer en su clave, que la 2.6.1 ya no escribe,
y el fichero no puede leer la clave de una tabla como hace el destino que
conecta, así que sus upserts nombran una clave que la tabla no tiene. El resto
del fichero se carga. -migrate -yes escribe en el fichero el borrado de esa
tabla, antes de las filas que vuelve a leer, así que el fichero reproducido en
orden carga entero: ver qué hace aplicarlo en cada
almacén.
A mano, tira la tabla, como describe la página de
medidas, y
vuelve a llenarla con un relleno histórico.
El sink de fichero y este no coinciden. Salvo por la clave de arriba, no
pueden: los dos renderizan el mismo esquema desde el mismo código, y cmd/check_postgres planifica contra él
cada consulta de panel. Si las tablas difieren, una se cargó desde una versión
anterior.