immobiliare/fastify-sentry

Can't get this package to work at all, am I missing something?

Opened this issue · 9 comments

This looks like a great wrapper for Sentry + Fastify. I'd love to use it in my project.

I don't know if I'm missing an important step in the instructions or something, but I cannot get this to work at all:

import fastifySentry from '@immobiliarelabs/fastify-sentry'
await fastify.register(fastifySentry, {
  dsn: process.env.SENTRY_DSN,
  debug: true,
  environment: process.env.SERVER_ENV,
  tracesSampleRate: 1.0,
  release: '1.0.0',
})
fastify.route({
  method: 'GET',
  url: '/test',
  handler: async (request, reply) => {
    throw new Error('test1234')
  },
})

I have the following issues:

  1. The error is never captured in my Sentry UI. The call to captureException in base.js is firing, but nothing is showing up in Sentry.
  2. Calling fastify.Sentry.captureMessage() doesn't work either
  3. Enabling tracing with tracesSampleRate: 1.0 does not work because if (hasTracingEnabled()) { in request.js evaluates to false.

I've ensured my SENTRY_DSN is correct, as it works when I use the Sentry Node SDK, and double checked your examples and I don't think I'm missing anything.

Any ideas would be appreciated!

Hi @abecks , it doesn't look you're missing anything, that seems strange 🤔 . I''l try to take a look at it and get back to you

I tried this code:

import Fastify from 'fastify'
import fastifySentry from '@immobiliarelabs/fastify-sentry'
const fastify = Fastify()

await fastify.register(fastifySentry, {
  dsn: process.env.SENTRY_DSN,
  debug: true,
  environment: process.env.SERVER_ENV,
  tracesSampleRate: 1.0,
  release: '1.0.0',
})
fastify.route({
  method: 'GET',
  url: '/test',
  handler: async (request, reply) => {
    throw new Error('test1234')
  },
})

fastify.listen({ port: 3000 })

this is the output I get on console:

Screenshot 2024-01-15 alle 10 02 15

And I correctly get an event on the public Sentry instance:

Screenshot 2024-01-15 alle 10 04 38

Not sure what's wrong 🤔

@abecks Can you share something more about your environment? I can't riproduce your issue .

@dnlup Sorry to dump that issue without further information. Been trying to strip away parts of my app to try to figure this one out. The weird thing is that the ultimate calls to Sentry.captureException return a sentryEventId.. but that ID doesn't exist in my Sentry account.

I'll keep working on it today/this week and let you know if I can figure out whats going on. Appreciate the help.

@dnlup

It looks like somehow a scope is being created that does not have a Sentry client attached, and Sentry internally short circuits without an error.

image

Edit: It also looks to be related to the tracing request handler. When I disable tracing, errors are showing up in Sentry!

@dnlup

If tracing is enabled, the tracingRequestHook runs before the errorWrapperRequestHandler. This appears to cause strange behavior, as fastify.Sentry.getCurrentHub().configureScope((scope) => { inside tracingRequestHook never fires. Somehow a scope is created that does not have a Sentry client associated with it.

I've found two possible solutions.

  1. Disable tracing
  2. Register the errorWrapperRequestHook before the tracingRequestHook:

lib/request.js ends with this block:

module.exports = function (fastify) {
  if (hasTracingEnabled()) {
    fastify.log.info('Sentry tracing enabled.');
    fastify.addHook('onRequest', tracingRequestHook(fastify));
    fastify.addHook('onResponse', tracingResponseHook(fastify));
  } else {
    fastify.log.info('Sentry tracing not enabled.');
  }
  fastify.addHook('onRequest', errorWrapperRequestHook(fastify)); // move this above the tracing hooks
};

Is there a reason the errorWrapperRequestHook is registered after the tracingRequestHook?

Also, in Sentry's official Koa guide, they register the hook with Sentry.runWithAsyncContext before the hook that handles transactions.

Edit with my versions:
Node 20
Fastify 4.25.2
@sentry/* 7.92.0
@immobiliarelabs/fastify-sentry 8.0.0

It looks like hub.configureScope is now deprecated, but updating it to the new syntax did not fix the problem.

Thank you @abecks for the detailed investigation, I'll try to reproduce it and migrate deprecated SDK apis and see if that changes this behavior.

Is there a reason the errorWrapperRequestHook is registered after the tracingRequestHook?

It is usually the last handler in the request response lifecycle, the fact that the tracing handler is registered before should not matter. It's really strange that you have a scope without a client associated 🤔

A couple of last questions, are you installing the SDK separately or are you using the one installed by the plugin? Also, does this happen also with the version 7 of the plugin? Thank you

I am sorry @abecks but I really can't reproduce this issue, I made a repo where we can make tests:

https://github.com/dnlup/fastify-sentry-tests

Feel free to use it and modify it to match your environment, if you have the time

ctkc commented

I'm having a similar issue with NestJs + Fastify. I figured that it works properly if I register a route in the main file like this:

app.getHttpAdapter().get("test-route", (req, res) => {
  throw new Error("Sentry test");
});

But it doesn't work if I throw an error from a controller or a GraphQL resolver, I'm not receiving the errors in Sentry.

I'm still debugging but I couldn't find where the problem is so far.