1. Querying Loki #
Faro signals are structured logs.
LogQL queries #
Each Faro signal arrives in Loki as a logfmt line, with a kind field (measurement, exception, log, event) and metadata (application, version, page, browser, session).
# Erreurs JavaScript par message
sum by (value) (count_over_time({app_name="boutique"} | logfmt | kind="exception" [1h]))
# LCP au 75e percentile par page
quantile_over_time(0.75, {app_name="boutique"} | logfmt | kind="measurement" | lcp != "" | unwrap lcp [15m]) by (page_url)
# Événements « ajout_panier » par version
sum by (app_version) (count_over_time({app_name="boutique"} | logfmt | kind="event" | event_name="ajout_panier" [1h]))Good to know: The exact label and field names depend on the Alloy version and your configuration: open a line in Explore to check them before writing a dashboard.
2. Dashboards and alerts #
Tracking the user experience.
A front-end dashboard #
| Panel | Content |
|---|---|
| Web Vitals p75 | LCP, INP, CLS per page and per version |
| Errors | Number of exceptions, top 10 messages, affected browsers |
| Volume | Sessions, page views |
| Slow requests | fetch traces > 1 s |
| Conversion | Business event funnel |
Alerts #
# Règle Loki (ruler) ou Grafana : pic d'erreurs JavaScript après un déploiement
sum(count_over_time({app_name="boutique"} | logfmt | kind="exception" [10m])) > 50Good practice: Always compare by app_version: an error increase limited to the latest version immediately points to the faulty deployment.3. GDPR and privacy #
Measuring without tracking.
Rules #
| Principle | Implementation |
|---|---|
| Consent | If collection is not strictly necessary, initialize Faro only after consent (consent banner) |
| Minimization | No email, name or form content; URLs cleaned of sensitive parameters |
| Pseudonymization | Technical user identifier, never a direct one |
| Sampling | samplingRate to collect only part of the sessions |
| Retention | Short Loki retention for this data (30 days for example) |
initializeFaro({
// ...
beforeSend: (item) => {
// retirer les paramètres d'URL des métadonnées de page
if (item.meta?.page?.url) item.meta.page.url = item.meta.page.url.split('?')[0];
return item;
},
ignoreErrors: [/ResizeObserver loop/, /Script error\./],
});My progress
Sign in to track your progress and take notes. Sign in
💬 Questions about this lesson
No questions yet: be the first to ask for help or share your configuration.
Course Glossary
Core Web Vitals
Set of three metrics defined by Google to measure the real experience of a web page: loading (LCP (Largest Contentful Paint)), responsiveness (INP (In...
LCP (Largest Contentful Paint)
Time until the largest visible element of the page (image, video or text block) is rendered: it shows when the main content appears. Loading metric of...
INP (Interaction to Next Paint)
Latency of interactions (click, tap, key press) observed over the whole visit: the delay between the user's action and the next paint. The reported va...
CLS (Cumulative Layout Shift)
Measure of visual stability: the sum of unexpected layout shifts (a button moving just as you click, text pushed down by an ad). Unitless, computed ov...
FCP (First Contentful Paint)
Time until the first content (text, image, SVG) is rendered: the moment the user sees the page start loading. It is not a Core Web Vital, but it helps...
TTFB (Time to First Byte)
Time between the start of navigation and the arrival of the first byte of the response: it adds up redirects, DNS, TCP/TLS connection and server proce...
FID (First Input Delay)
Former responsiveness metric of the Core Web Vitals: the delay before the browser starts handling the first interaction (good ≤ 100 ms). It ignored la...
TBT (Total Blocking Time)
Lab metric (Lighthouse): the sum, between FCP (First Contentful Paint) and the end of loading, of the blocking part of each long task (over 50 ms) on ...
CrUX (Chrome UX Report)
Google's public dataset aggregating the Core Web Vitals measured from real Chrome users (at the 75th percentile, per origin and URL, over a rolling 28...
Lighthouse
Google's free audit tool, built into Chrome DevTools and PageSpeed Insights: it loads the page in a simulated environment and scores performance, acce...
Apdex
Application Performance Index: a satisfaction score between 0 and 1 based on a time threshold T. Requests under T are “satisfied”, between T and 4T “t...
Recommended Articles
Front-end observability best practices with Faro
Checklist for useful, respectful RUM: SDK configuration, versions, source maps, correlation with ...
Faro and Alloy: receiving front-end RUM with faro.receiver
Configure faro.receiver: CORS, API key, rate limiting, source maps, then send browser errors, Web...
From click to database: front-end to back-end traces with Faro
Link browser requests to back-end traces: TracingInstrumentation, traceparent header propagation,...
Real User Monitoring (RUM) and Core Web Vitals: measuring what users experience
Why observe the front end, what RUM measures, Core Web Vitals (LCP, INP, CLS) and their threshold...
Grafana Faro: architecture and installation
Install Grafana Faro: the web SDK (npm or CDN), Alloy's faro.receiver, sending to Loki and Tempo,...
Faro: JavaScript errors, logs, business events and sessions
Use the Faro API: automatic error capture, manual error reporting, logs, business events and meas...
Case study: this site's minimal RUM, cookie-free, exposed to Prometheus
How this site measures its Core Web Vitals with about forty lines of JavaScript, an anonymous bea...
Conversion funnels in RUM: measuring where users drop off
Building and reading a conversion funnel with RUM data: steps, rates, order, pitfalls, and implem...
Website monitoring: availability, HTTPS monitoring, certificates and performance
Set up website monitoring: availability and HTTPS checks, certificate expiry, response time, Core...