Next.js
Two files, one import. The same @naijacloud/argus/next import picks the server build in one and the browser build in the other.
Install
npm install @naijacloud/argusSet up
Add two files at the root of your app (next to app/, or inside src/ if
you use one):
import { init } from '@naijacloud/argus/next'
export const register = () => init({ dsn: 'https://<public key>@argus-in.naijacloud.com/<project id>' })On Next.js 15 and later, also export the request-error hook from
instrumentation.ts, so errors in route handlers, server actions and
rendering are reported:
export { onRequestError } from '@naijacloud/argus/next'The DSN's key is public, so it's safe in the browser file. To keep it out of
your code, read it from the environment: process.env.ARGUS_DSN on the
server and process.env.NEXT_PUBLIC_ARGUS_DSN in the browser. On the server,
init() with no dsn reads ARGUS_DSN, then SENTRY_DSN, which a
Naijacloud service gets from its Send errors to Argus switch.
Send a test event
npx @naijacloud/argus test --dsn https://<public key>@argus-in.naijacloud.com/<project id>It sends one test event and says whether Argus accepted it. Without --dsn
it uses ARGUS_DSN.
What it captures
- On the server (the Node.js runtime): uncaught exceptions and unhandled
rejections, every incoming request traced, outgoing
fetch()calls as spans, and withonRequestError, errors from route handlers, server actions and rendering, named after the route. - In the browser: uncaught errors and promise rejections, with
breadcrumbs of clicks (which element, never what was typed), navigation,
console,fetchand XHR. Errors raised offline are kept and sent when the browser is back online. - In the Edge runtime,
init()does nothing. Middleware and edge routes are not reported.
Report errors yourself
import { captureException, setUser } from '@naijacloud/argus/next'
setUser({ id: session.userId })
try {
await chargeCard(order)
} catch (err) {
captureException(err, { tags: { provider: 'paystack' } })
}Logs, metrics and traces
import { log, metrics, trace } from '@naijacloud/argus/next'
export async function POST(req: Request) {
const order = await req.json()
log.info('payment started', { orderId: order.id })
metrics.count('payments.started', 1, { method: 'card' })
await trace('charge card', async (span) => {
span?.setAttribute('provider', 'paystack')
await paystack.charge(order)
})
return Response.json({ ok: true })
}Logs are sent every 5 seconds and metrics every 10. More in Node.js.
Cron check-ins and feature flags
import { cron, flags } from '@naijacloud/argus/next'
// Create the monitor in Argus first.
await cron.withMonitor('nightly-invoices', () => sendInvoices())
if (await flags.isOn('new-checkout', user.id)) {
// …
}withMonitor reports the start, then success or failure. A flag check
returns your fallback (false here) if Argus can't be reached. Answers are
cached for 30 seconds per user.
Release and environment
On the server, the SDK reads ARGUS_RELEASE and ARGUS_ENVIRONMENT, then
SENTRY_RELEASE and SENTRY_ENVIRONMENT. The browser can't read those, so
pass them in instrumentation-client.ts, from variables set at build time:
init({
dsn: process.env.NEXT_PUBLIC_ARGUS_DSN,
release: process.env.NEXT_PUBLIC_RELEASE,
environment: 'production',
})The environment is production when none is set.
Privacy
On by default, in both files:
- Values of keys such as
password,token,secret,authorization,cookie,bvnandcardbecome[Filtered], at any depth. - Card numbers, bearer tokens and JWTs are filtered inside strings.
- Query strings are removed from URLs in breadcrumbs and spans.
- Clicks record the element, never what was typed.
- The user's IP address is not sent unless you set
sendDefaultPii: true.
Pass beforeSend to init() to change an event, or return null to drop
it:
init({
beforeSend: (event) =>
event.exception?.values.at(-1)?.value.includes('ResizeObserver') ? null : event,
})Already on Sentry
Keep @sentry/nextjs. In sentry.server.config.ts and
sentry.client.config.ts, change the dsn line:
dsn: 'https://<public key>@argus-in.naijacloud.com/<project id>',Source maps
Browser stack traces point at minified bundles until you upload your build's
source maps. Set productionBrowserSourceMaps: true in next.config, pass
the same release to the SDK and to the upload, and follow
Source maps.