Skip to content

test(node): Add tests for Undici #7628

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

Merged
merged 12 commits into from
Mar 29, 2023
Merged
Prev Previous commit
Next Next commit
update to latest dc
  • Loading branch information
AbhiPrasad committed Mar 29, 2023
commit 9d1ba89bd9e911b188b9713568fce3e5a8c4777e
41 changes: 40 additions & 1 deletion packages/node/src/integrations/diagnostics_channel.d.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
// Vendored from https://github.com/DefinitelyTyped/DefinitelyTyped/blob/8fc6d58e6434810867a9483e2107ea51bfca9153/types/node/diagnostics_channel.d.ts
// Vendored from https://github.com/DefinitelyTyped/DefinitelyTyped/blob/5a94716c6788f654aea7999a5fc28f4f1e7c48ad/types/node/diagnostics_channel.d.ts

// License:
// This project is licensed under the MIT license.
Expand Down Expand Up @@ -77,6 +77,45 @@ declare module 'diagnostics_channel' {
*/
function channel(name: string | symbol): Channel;
type ChannelListener = (message: unknown, name: string | symbol) => void;
/**
* Register a message handler to subscribe to this channel. This message handler will be run synchronously
* whenever a message is published to the channel. Any errors thrown in the message handler will
* trigger an 'uncaughtException'.
*
* ```js
* import diagnostics_channel from 'diagnostics_channel';
*
* diagnostics_channel.subscribe('my-channel', (message, name) => {
* // Received data
* });
* ```
*
* @since v18.7.0, v16.17.0
* @param name The channel name
* @param onMessage The handler to receive channel messages
*/
function subscribe(name: string | symbol, onMessage: ChannelListener): void;
/**
* Remove a message handler previously registered to this channel with diagnostics_channel.subscribe(name, onMessage).
*
* ```js
* import diagnostics_channel from 'diagnostics_channel';
*
* function onMessage(message, name) {
* // Received data
* }
*
* diagnostics_channel.subscribe('my-channel', onMessage);
*
* diagnostics_channel.unsubscribe('my-channel', onMessage);
* ```
*
* @since v18.7.0, v16.17.0
* @param name The channel name
* @param onMessage The previous subscribed handler to remove
* @returns `true` if the handler was found, `false` otherwise
*/
function unsubscribe(name: string | symbol, onMessage: ChannelListener): boolean;
/**
* The class `Channel` represents an individual named channel within the data
* pipeline. It is use to track subscribers and to publish messages when there
Expand Down
36 changes: 9 additions & 27 deletions packages/node/src/integrations/undici.ts
Original file line number Diff line number Diff line change
Expand Up @@ -56,11 +56,6 @@ export class Undici implements Integration {
*/
public name: string = Undici.id;

// Have to hold all built channels in memory otherwise they get garbage collected
// See: https://github.com/nodejs/node/pull/42714
// This has been fixed in Node 19+
private _channels = new Set<DiagnosticsChannel.Channel>();

private readonly _options: UndiciOptions;

public constructor(_options: Partial<UndiciOptions> = {}) {
Expand All @@ -82,13 +77,12 @@ export class Undici implements Integration {
// no-op
}

if (!ds) {
if (!ds || !ds.subscribe) {
return;
}

// https://github.com/nodejs/undici/blob/e6fc80f809d1217814c044f52ed40ef13f21e43c/docs/api/DiagnosticsChannel.md
const requestCreateChannel = this._setupChannel(ds, ChannelName.RequestCreate);
requestCreateChannel.subscribe(message => {
ds.subscribe(ChannelName.RequestCreate, message => {
const { request } = message as RequestCreateMessage;

const url = new URL(request.path, request.origin);
Expand All @@ -105,12 +99,12 @@ export class Undici implements Integration {
const activeSpan = scope.getSpan();

if (activeSpan && client) {
const options = client.getOptions();
const clientOptions = client.getOptions();

// eslint-disable-next-line deprecation/deprecation
const shouldCreateSpan = options.shouldCreateSpanForRequest
const shouldCreateSpan = clientOptions.shouldCreateSpanForRequest
? // eslint-disable-next-line deprecation/deprecation
options.shouldCreateSpanForRequest(stringUrl)
clientOptions.shouldCreateSpanForRequest(stringUrl)
: true;

if (shouldCreateSpan) {
Expand All @@ -131,9 +125,9 @@ export class Undici implements Integration {
request.__sentry__ = span;

// eslint-disable-next-line deprecation/deprecation
const shouldPropagate = options.tracePropagationTargets
const shouldPropagate = clientOptions.tracePropagationTargets
? // eslint-disable-next-line deprecation/deprecation
stringMatchesSomePattern(stringUrl, options.tracePropagationTargets)
stringMatchesSomePattern(stringUrl, clientOptions.tracePropagationTargets)
: true;

if (shouldPropagate) {
Expand All @@ -151,8 +145,7 @@ export class Undici implements Integration {
}
});

const requestEndChannel = this._setupChannel(ds, ChannelName.RequestEnd);
requestEndChannel.subscribe(message => {
ds.subscribe(ChannelName.RequestEnd, message => {
const { request, response } = message as RequestEndMessage;

const url = new URL(request.path, request.origin);
Expand Down Expand Up @@ -188,8 +181,7 @@ export class Undici implements Integration {
}
});

const requestErrorChannel = this._setupChannel(ds, ChannelName.RequestError);
requestErrorChannel.subscribe(message => {
ds.subscribe(ChannelName.RequestError, message => {
const { request } = message as RequestErrorMessage;

const url = new URL(request.path, request.origin);
Expand Down Expand Up @@ -224,14 +216,4 @@ export class Undici implements Integration {
}
});
}

/** */
private _setupChannel(
ds: typeof DiagnosticsChannel,
name: Parameters<typeof DiagnosticsChannel.channel>[0],
): DiagnosticsChannel.Channel {
const channel = ds.channel(name);
this._channels.add(channel);
return channel;
}
}