Enviar eventos de analítica
Una función de retorno, cinco eventos, ningún proveedor — conecta las interacciones del lector en duxt con la analítica que ya tienes.
duxt informa de lo que los lectores hacen con un sitio de documentación — buscar, copiar un comando, probar un endpoint, responder «¿Te ha resultado útil esta página?» — a una única función que escribes tú. No entrega ningún proveedor, ningún SDK y ningún script, y un sitio que no haya escrito esa función no informa de nada y no descarga nada extra.
No hay destino por defecto, porque una capa de documentación no puede elegir uno
para los lectores de otra persona. Sin duxt.analytics.track, cada punto de
llamada de abajo alcanza una función que no existe y se detiene.
Pasos
- Escribe la función de retorno. Vive en
app.config.ts, junto al resto de tu configuración de duxt, y recibe un evento por interacción:export default defineAppConfig({ duxt: { analytics: { track(event) { // `event.name` es el discriminante; `event.context` dice en qué // página, locale, fuente y versión ocurrió. console.log(event.name, event.context.path); } } } });
La función de retorno se ejecuta solo en el navegador. Una compilación y un prerrenderizado no la llaman nunca, así que un renderizado estático no te llena la analítica con páginas que abrió un rastreador. - Envíalo adonde ya vive tu analítica. Lo que exponga tu proveedor — un SDK
que ya esté en la página, o una ruta propia para que el navegador del lector
nunca hable con un tercero que no elegiste:
export default defineAppConfig({ duxt: { analytics: { track(event) { const { name, context, ...properties } = event; // Tu proveedor, tus nombres de propiedad, tu barrera de // consentimiento. window.plausible?.(name, { props: { ...context, ...properties } }); } } } });
duxt no pone ninguna cookie, no almacena nada, no acumula nada en búfer y no
muestra ningún aviso de consentimiento — no tiene nada que preguntar, porque
nada sale de la página salvo a través de tu función. Eso también significa
que la barrera es tuya: si tu política de privacidad exige consentimiento
antes de que esto llegue a un proveedor, compruébalo dentro de track y sal
antes de tiempo.
- Elige los eventos que quieres y descarta el resto. La unión es cerrada,
así que un
switchla cubre de forma exhaustiva y lo que no nombres simplemente no se envía:
track(event) {
if (event.name === 'search' && event.results === 0) {
// El único informe que casi siempre quiere un sitio de documentación:
// un término que alguien buscó y que el sitio no supo responder.
report('docs-search-miss', { query: event.query, ...event.context });
}
}
- Comprueba que llega un evento, con el contexto que esperabas — bajo un prefijo de versión y de locale, no solo en la URL desnuda.
Los eventos
Cada evento tiene un name, sus propios campos y un context.
name | Se emite cuando | Lleva |
|---|---|---|
search | Se estabiliza una consulta no vacía tras el antirrebote — incluida una que no encontró nada | query, results, approximate |
search-result | Un lector abre un resultado | query, rank, to, collection |
copy | Se copia un ejemplo de código propio de la capa | kind, language, manager, sample |
api-request | Se asienta una petición de prueba | operation, method, path, outcome, statusClass, duration |
feedback | Un lector responde «¿Te ha resultado útil esta página?» | helpful |
search se emite una vez por consulta estabilizada, no por pulsación: el
antirrebote descarta lo que nadie terminó de escribir, y un resultado al que
otro más nuevo deja obsoleto no se informa nunca, porque el lector no llegó a
verlo.
copy cubre los ejemplos de código propios de la capa — un bloque delimitado,
un ::code-group, un bloque ::package-managers, una muestra de petición en el
cliente de pruebas — y kind dice cuál. «Copiar la página como Markdown» no
está en esta familia y no emite nada: es la página, no un ejemplo dentro de
ella.
api-request describe la operación tal y como la declara el documento
OpenAPI. path es la plantilla (/pets/{id}), nunca la URL a la que se
llamó.
El contexto
| Campo | Notas |
|---|---|
path | La ruta de la documentación, sin el prefijo de locale, la cadena de consulta ni el fragmento |
locale | El locale en el que se leyó la página |
source | De qué fuente salió la página — ausente en un sitio de una sola fuente |
version | Qué versión — ausente donde la fuente solo tiene una |
Lo que nunca se envía
Esta lista es el sentido de la función, así que conviene decirlo claro. Ningún evento lleva:
- una credencial, cabecera o token de API;
- un cuerpo de petición o de respuesta, ni una URL de petición concreta;
- el texto que se copió;
- el contenido representado de un resultado de búsqueda;
- un identificador de navegador, de sesión o de lector de ningún tipo;
- la cadena de consulta o el fragmento de la propia ruta de la página.
duxt tampoco transmite, acumula en búfer ni persiste nada por su cuenta. En la capa no hay cola, ni reintento, ni almacenamiento, ni llamada de red: tu función es lo único que sale de la página.
Nunca se espera a tu función de retorno, y lo que lance o con lo que rechace se descarta — un proveedor caído no debe llevarse por delante la búsqueda, la copia, la opinión ni la petición.
Opiniones de página, por las dos vías
feedback es la misma respuesta que DuxtPageFeedback ha emitido siempre. El
evento @feedback del componente y su slot por defecto no cambian, así que
envolverlo sigue funcionando y ninguna de las
dos vías necesita a la otra — usa la función de retorno de analítica si quieres
un único destino para todo, y la envoltura si la opinión por sí sola va a un
sitio propio.
Lista de comprobación
-
duxt.analytics.trackestá definido, y no hizo falta nada más para activarlo - El destino es tuyo — un proveedor que elegiste, o una ruta propia
- El consentimiento se comprueba dentro de
track, si tu política lo pide - Llegó un evento con la ruta, el locale, la fuente y la versión que esperabas
- Nada de lo que reenvías identifica al lector