
Security News
Socket Releases Free Certified Patches for Critical vm2 Sandbox Escape
A critical vm2 sandbox escape can allow untrusted JavaScript to break isolation and execute commands on the host Node.js process.
@hono/prometheus
Advanced tools
This middleware adds basic RED metrics to your Hono application, and exposes them on the /metrics endpoint for Prometheus to scrape.
This package depends on prom-client, so you need to install that as well:
npm install -S @hono/prometheus prom-client
# or
yarn add @hono/prometheus prom-client
import { prometheus } from '@hono/prometheus'
import { Hono } from 'hono'
const app = new Hono()
const { printMetrics, registerMetrics } = prometheus()
app.use('*', registerMetrics)
app.get('/metrics', printMetrics)
app.get('/', (c) => c.text('foo'))
export default app
Making a GET request to /metrics returns the string representation of the metrics:
# HELP http_request_duration_seconds Duration of HTTP requests in seconds
# TYPE http_request_duration_seconds histogram
http_request_duration_seconds_bucket{le="0.005",method="GET",route="/",status="200",ok="true"} 2
http_request_duration_seconds_bucket{le="0.01",method="GET",route="/",status="200",ok="true"} 2
http_request_duration_seconds_bucket{le="0.025",method="GET",route="/",status="200",ok="true"} 2
http_request_duration_seconds_bucket{le="0.05",method="GET",route="/",status="200",ok="true"} 2
http_request_duration_seconds_bucket{le="0.075",method="GET",route="/",status="200",ok="true"} 2
http_request_duration_seconds_bucket{le="0.1",method="GET",route="/",status="200",ok="true"} 2
http_request_duration_seconds_bucket{le="0.25",method="GET",route="/",status="200",ok="true"} 2
http_request_duration_seconds_bucket{le="0.5",method="GET",route="/",status="200",ok="true"} 2
http_request_duration_seconds_bucket{le="0.75",method="GET",route="/",status="200",ok="true"} 2
http_request_duration_seconds_bucket{le="1",method="GET",route="/",status="200",ok="true"} 2
http_request_duration_seconds_bucket{le="2.5",method="GET",route="/",status="200",ok="true"} 2
http_request_duration_seconds_bucket{le="5",method="GET",route="/",status="200",ok="true"} 2
http_request_duration_seconds_bucket{le="7.5",method="GET",route="/",status="200",ok="true"} 2
http_request_duration_seconds_bucket{le="10",method="GET",route="/",status="200",ok="true"} 2
http_request_duration_seconds_bucket{le="+Inf",method="GET",route="/",status="200",ok="true"} 2
http_request_duration_seconds_sum{method="GET",route="/",status="200",ok="true"} 0.000251125
http_request_duration_seconds_count{method="GET",route="/",status="200",ok="true"} 2
http_request_duration_seconds_bucket{le="0.005",method="GET",route="/user/:id",status="200",ok="true"} 3
http_request_duration_seconds_bucket{le="0.01",method="GET",route="/user/:id",status="200",ok="true"} 3
http_request_duration_seconds_bucket{le="0.025",method="GET",route="/user/:id",status="200",ok="true"} 3
http_request_duration_seconds_bucket{le="0.05",method="GET",route="/user/:id",status="200",ok="true"} 3
http_request_duration_seconds_bucket{le="0.075",method="GET",route="/user/:id",status="200",ok="true"} 3
http_request_duration_seconds_bucket{le="0.1",method="GET",route="/user/:id",status="200",ok="true"} 3
http_request_duration_seconds_bucket{le="0.25",method="GET",route="/user/:id",status="200",ok="true"} 3
http_request_duration_seconds_bucket{le="0.5",method="GET",route="/user/:id",status="200",ok="true"} 3
http_request_duration_seconds_bucket{le="0.75",method="GET",route="/user/:id",status="200",ok="true"} 3
http_request_duration_seconds_bucket{le="1",method="GET",route="/user/:id",status="200",ok="true"} 3
http_request_duration_seconds_bucket{le="2.5",method="GET",route="/user/:id",status="200",ok="true"} 3
http_request_duration_seconds_bucket{le="5",method="GET",route="/user/:id",status="200",ok="true"} 3
http_request_duration_seconds_bucket{le="7.5",method="GET",route="/user/:id",status="200",ok="true"} 3
http_request_duration_seconds_bucket{le="10",method="GET",route="/user/:id",status="200",ok="true"} 3
http_request_duration_seconds_bucket{le="+Inf",method="GET",route="/user/:id",status="200",ok="true"} 3
http_request_duration_seconds_sum{method="GET",route="/user/:id",status="200",ok="true"} 0.000391333
http_request_duration_seconds_count{method="GET",route="/user/:id",status="200",ok="true"} 3
# HELP http_requests_total Total number of HTTP requests
# TYPE http_requests_total counter
http_requests_total{method="GET",route="/",status="200",ok="true"} 2
http_requests_total{method="GET",route="/user/:id",status="200",ok="true"} 3
An options object can be passed in the prometheus() middleware factory to configure the metrics:
prefixType: string
Prefix all metrics with this string.
registryType: Registry
A prom-client Registry instance to store the metrics. If not provided, a new one will be created.
Useful when you want to register some custom metrics while exposing them on the same /metrics endpoint that this middleware creates. In this case, you can create a Registry instance, register your custom metrics on that, and pass that into this option.
collectDefaultMetricsType: boolean | CollectDefaultMetricsOptions
There are some default metrics recommended by prom-client, like event loop delay, garbage collection statistics etc.
To enable these metrics, set this option to true. To configure the default metrics, pass an object with the configuration options.
metricOptionsType: object (see below)
Modify the standard metrics (requestDuration and requestsTotal) with any of the Counter / Histogram metric options, including:
disabledType: boolean
Disables the metric.
customLabelsType: Record<string, (context) => string>
A record where the keys are the labels to add to the metrics, and the values are functions that receive the Hono context and return the value for that label. This is useful when adding labels to the metrics that are specific to your application or your needs. These functions are executed after all the other middlewares finished.
The following example adds a label to the requestsTotal metric with the contentType name where the value is the content type of the response:
app.use(
'*',
prometheus({
metricOptions: {
requestsTotal: {
customLabels: {
content_type: (c) => c.res.headers.get('content-type'),
},
},
},
})
)
If you want to expose custom metrics on the /metrics endpoint, you can create a Registry instance and pass it to the prometheus() factory function using the registry property:
import { prometheus } from '@hono/prometheus'
import { Hono } from 'hono'
import { Counter, Registry } from 'prom-client'
const registry = new Registry()
const customCounter = new Counter({
name: 'custom_counter',
help: 'A custom counter',
registers: [registry],
})
const app = new Hono()
const { printMetrics, registerMetrics } = prometheus({
registry,
})
app.use('*', registerMetrics)
app.get('/metrics', printMetrics)
app.get('/', (c) => c.text('foo'))
export default app
// Somewhere in your application you can increment the custom counter:
customCounter.inc()
David Dios https://github.com/dios-david
MIT
FAQs
Prometheus metrics middleware for Hono
The npm package @hono/prometheus receives a total of 45,016 weekly downloads. As such, @hono/prometheus popularity was classified as popular.
We found that @hono/prometheus demonstrated a healthy version release cadence and project activity because the last version was released less than a year ago. It has 1 open source maintainer collaborating on the project.
Did you know?

Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.

Security News
A critical vm2 sandbox escape can allow untrusted JavaScript to break isolation and execute commands on the host Node.js process.

Research
Five malicious NuGet packages impersonate Chinese .NET libraries to deploy a stealer targeting browser credentials, crypto wallets, SSH keys, and local files.

Security News
pnpm 11 turns on a 1-day Minimum Release Age and blocks exotic subdeps by default, adding safeguards against fast-moving supply chain attacks.