Faro
Grafana just released Faro, an open source project for application frontend observability that enables an easy way to track the health of your web applications.
Faro provides a JavaScript library you can add to your frontend application to collect logs, errors, and performance metrics, add metadata and forward it to the Grafana Agent which writes data to Prometheus, Loki, or Tempo.
This sounds very exciting!
Will Faro work with qryn out of the box? Let's look at the app diagram:
Loki, Prometheus and Tempo - this sounds like a perfect polyglot match!
Let's go instrument webapps using Faro and our ClickHouse powered stack!
Grafana Agent
The recipe uses a Grafana Agent powered public collector endpoint to receive and forward webapplication telemetry to Loki, Tempo, and Prometheus... or just qryn. Since we are drop-in compatible, all we have to change are the API URL endpoints.
metrics:
wal_directory: /tmp/wal
global: {}
configs:
- name: default
remote_write:
- url: https://qryn:3100/api/prom/push
basic_auth:
username: xxx
password: xxx
logs:
positions_directory: /tmp/loki-pos
configs:
- name: default
scrape_configs: []
clients:
- url: https://xxx:xxx@qryn:3100/loki/api/v1/push
traces:
configs:
- name: default
remote_write:
- endpoint: qryn:3100
basic_auth:
username: xxx
password: xxx
receivers:
otlp:
protocols:
grpc:
http:
cors:
allowed_origins:
- http://localhost:1234
max_age: 7200
integrations:
app_agent_receiver_configs:
- autoscrape:
enable: true
metrics_instance: 'default'
api_key: 'secret' # optional, if set, client will be required to provide it via x-api-key header
instance: 'frontend'
logs_instance: 'default'
traces_instance: 'default'
server:
host: 0.0.0.0
port: 12345
cors_allowed_origins:
- 'https://my-app.example.com'
logs_labels: # labels to add to loki log record
app: frontend # static value
kind: # value will be taken from log items. exception, log, measurement, etc
logs_send_timeout: 5000
sourcemaps:
download: true # will download source file, extract source map location,
# download source map and use it to transform stack trace locations
Faro SDK
The Grafana Faro Web SDK comes baked with a lot of useful features:
- Set up in seconds with just two lines of code
- Lightweight
- Automatic instrumentation that captures errors, logs, and performance metrics
- Pre-configured tracing system based on OpenTelemetry with automatic instrumentations
- Easy-to-use API for manual instrumentation
- Fully customizable and extensible
Follow the integration document to instrument your webapplication.
Take your sweet time to follow the tutorial
SDK Example
We can refer to the Grafana example for manually sending some test data.
import { LogLevel } from '@grafana/faro-web-sdk';
// there's a global property
const faro = window.faro;
// send a log message
// by default info, warn and error levels are captured.
// trace, debug and log are not
console.info('Hello world', 123);
// or
faro.api.pushLog(['Hello world', 123], { level: LogLevel.Debug });
// log with context
faro.api.pushLog(['Sending update'], {
context: {
payload: thePayload,
},
level: LogLevel.TRACE,
});
// set user metadata, to be included with every event. All properties optional
faro.api.setUser({
email: 'bob@example.com',
id: '123abc',
username: 'bob',
attributes: {
role: 'manager',
},
});
// unset user
faro.api.resetUser();
// set session metadata, to be included with every event
faro.api.setSession(createSession({ plan: 'paid' }));
// unset session
faro.api.resetSession();
// push measurement
faro.api.pushMeasurement({
type: 'cart-transaction',
values: {
delay: 122,
duration: 4000,
},
});
// push an error
faro.api.pushError(new Error('everything went horribly wrong'));
// push an event
faro.api.pushEvent('navigation', { url: window.location.href });
// pause faro, preventing events from being sent
faro.pause();
// resume sending events
faro.unpause();
Sample Dashboards
Last but not least, include the sample dashboards to complete your setup.
Update
Jachen tried using Faro and came up with his tiny alternative: boscaiolog
Conclusion
Faro is compatible with qryn out of the box. And qryn is amazing. 💛