Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Sentry headers are not sent in sentry/browser, instead it is sent in query params #1992

Closed
4 of 8 tasks
SamvelRaja opened this issue Apr 3, 2019 · 15 comments
Closed
4 of 8 tasks
Assignees

Comments

@SamvelRaja
Copy link

Package + Version

  • @sentry/browser
  • @sentry/node
  • raven-js
  • raven-node (raven for node)
  • other:

Version:

4.6.4

Description

Though from the new sentry/browser sdk the support for sending sentry_secret is dropped.
It is not sending the remaining query params

  • sdk_version
  • sentry_key
    in headers. And there is no option to handle configure this as well.
    I hope this is supported in @sentry/node.

Sample url generated in @sentry/browser is

https://[DSN]/?sentry_key=SENTRY_KEY&sentry_version=7
@HazAT
Copy link
Member

HazAT commented Apr 3, 2019

Can you elaborate how this surfaces into an error or bug on your side?

@HazAT HazAT self-assigned this Apr 3, 2019
@SamvelRaja
Copy link
Author

@HazAT Thanks for the response.
It is not the bug or error, It is the expected practice to send the information in headers rather in queryparams.

https://docs.sentry.io/development/sdk-dev/overview/#authentication

Hence, I expect this to be available in the SDK..

@HazAT
Copy link
Member

HazAT commented Apr 4, 2019

Yeah, I mean since this is not breaking anything right now we won't change it since we have more important things to work on. We are open to receiving PRs :)

@SamvelRaja
Copy link
Author

@HazAT Thanks 👍

@jetxr
Copy link

jetxr commented May 25, 2021

EasyPrivacy is blocking any POST requests with ?sentry_key in the URL. So ad-blockers using EasyPrivacy list (e.g. uBlock Origin) end up blocking Sentry even when using a relay.

Is it possible to make this configurable? I understand sending the information in headers will cause a pre-flight request.. But it's kind of essential to bypass ad-blockers when using a relay.

@kamilogorek
Copy link
Contributor

@jetxr we are in the process of writing a workaround for this issue. I'll keep this issue updated once we release it.

@alexm92
Copy link

alexm92 commented Jun 11, 2021

I'm also looking forward to this workaround.

  1. Do you have any estimation on when it'll be ready?
  2. Do you need any help (I could try to contribute if needed)?

@kamilogorek
Copy link
Contributor

@alexm92 the implementation on the SDK side is already done here - #3521
We just need few changes in the Sentry itself now to make it work.

@kamilogorek
Copy link
Contributor

The original issue seems to be outdated. As for dealing with adblockers, the solution has been shipped in 6.7.0 and explained in the new documentation section here: https://docs.sentry.io/platforms/javascript/troubleshooting/#using-the-tunnel-option

Cheers!

@alexm92
Copy link

alexm92 commented Jun 14, 2021

Hi @kamilogorek,

I just tried to use this and I was unable to make it work. I get 400 Bad Request with {"detail":"invalid event envelope","causes":["invalid item header","missing field `type` at line 1 column 21"]}

Here's my code:

async function handleRequest(request) {
  const envelope = await request.text();

  const pieces = envelope.split('\n', 2);
  const header = JSON.parse(pieces[0]);

  if (header?.dsn) {
    console.log('Found DSN', header.dsn);
    const dsn = new URL(header.dsn);

    const projectId = parseInt(dsn.pathname.slice(1)
      .split('/')[0]);
    const options = {
      headers: {
        'Content-Type': 'text/plain;charset=UTF-8',
      },
      method: 'POST',
      body: envelope,
    };

    const response = await fetch(`https://${dsn.host}/api/${projectId}/envelope/`, options);
    // do something with response
  }

  return new Response('OK', {
    headers: {
      'Content-Type': 'text/plain',
      'Access-Control-Allow-Origin': '*',
    },
  })
}

Am I doing something wrong?

@kamilogorek
Copy link
Contributor

@alexm92 no, I messed up, sorry about that. Fix is on it's way #3676
In the meantime, here's a quick workaround:

const parseEnvelope = (body) => {
  const [envelopeHeaderString, itemHeaderString, itemString] = body.split("\n");

  return {
    envelopeHeader: JSON.parse(envelopeHeaderString),
    itemHeader: JSON.parse(itemHeaderString),
    item: JSON.parse(itemString),
  };
};

async function handleRequest(request) {
  const body = await request.text();
  const { envelopeHeader, itemHeader, item } = parseEnvelope(body);

  if (envelopeHeader.dsn) {
    const dsn = new URL(header.dsn);
    itemHeader.type = itemHeader.type ?? 'event';
    const envelope = `${JSON.stringify(envelopeHeader)}\n${JSON.stringify(itemHeader)}\n${JSON.stringify(item)}`
    const options = {
      headers: {
        'Content-Type': 'application/octet-stream',
      },
      method: 'POST',
      body: envelope,
    };

    const response = await fetch(`https://${dsn.host}/api/${dsn.pathname}/envelope/`, options);
    // do something with response
  }

  return new Response('OK', {
    headers: {
      'Content-Type': 'text/plain',
      'Access-Control-Allow-Origin': '*',
    },
  })
}

@alexm92
Copy link

alexm92 commented Jun 15, 2021

Awesome, thanks @kamilogorek

Did some more changes and ended up using the following as serverless API on Cloudflare Workers.

addEventListener('fetch', event => {
  event.respondWith(handleRequest(event.request))
})

const corsAllowedDomains = new Set([
  'https://example.com',
]);


/**
 * Process the envelope header sent by Sentry client
 *
 * @param body
 * @returns {{item: any, envelopeHeader: any, itemHeader: any}}
 */
const parseEnvelope = (body) => {
  const [envelopeHeaderString, itemHeaderString, itemString] = body.split("\n");

  return {
    envelopeHeader: JSON.parse(envelopeHeaderString),
    itemHeader: JSON.parse(itemHeaderString),
    item: JSON.parse(itemString),
  };
};


/**
 * Respond with OK or Sentry response
 *
 * @param {Request} request
 */
async function handleRequest(request) {
  const defaultResponse = new Response('OK');
  const originHeader = request.headers.get('Origin');

  if (corsAllowedDomains.has(originHeader)) {
    defaultResponse.headers.set('Access-Control-Allow-Origin', originHeader);
  }

  const body = await request.text();
  const { envelopeHeader, itemHeader, item } = parseEnvelope(body);

  if (envelopeHeader?.dsn) {
    const dsn = new URL(envelopeHeader.dsn);
    itemHeader.type = itemHeader.type ?? 'event';

    const envelope = `${JSON.stringify(envelopeHeader)}\n${JSON.stringify(itemHeader)}\n${JSON.stringify(item)}`
    const projectId = parseInt(dsn.pathname.slice(1).split('/')[0]);
    const options = {
      headers: {
        'Content-Type': 'application/octet-stream',
      },
      method: 'POST',
      body: envelope,
    };

    // Proxy request to Sentry ingest
    const sentryResponse = await fetch(`https://${dsn.host}/api/${projectId}/envelope/`, options);

    // Reconstruct the Response object to make its headers mutable.
    const response = new Response(sentryResponse.body, sentryResponse);
    if (corsAllowedDomains.has(originHeader)) {
      response.headers.set('Access-Control-Allow-Origin', originHeader);
    }

    return response;
  }

  return defaultResponse;
}

@ping-localhost
Copy link

Thank you @alexm92 (and @kamilogorek) this tunnel is very useful. That said, I noticed that Sentry session tracking events do not send the DSN. Is that on purpose?

@kamilogorek
Copy link
Contributor

kamilogorek commented Jun 15, 2021

Thanks for catching that @ping-localhost #3680

@kamilogorek
Copy link
Contributor

kamilogorek commented Jun 15, 2021

@ping-localhost @alexm92 both fixes released in 6.7.1.

You can remove this part from your code:

itemHeader.type = itemHeader.type ?? 'event';
const envelope = `${JSON.stringify(envelopeHeader)}\n${JSON.stringify(itemHeader)}\n${JSON.stringify(item)}`

And pass body directly to the request instead of envelope.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

6 participants