dd-trace
Version:
Datadog APM tracing client for JavaScript
79 lines (64 loc) • 2.05 kB
JavaScript
const shimmer = require('../../datadog-shimmer')
const { addHook, channel } = require('./helpers/instrument')
const parseFinishedChannel = channel('datadog:url:parse:finish')
const urlGetterChannel = channel('datadog:url:getter:finish')
const instrumentedGetters = ['host', 'origin', 'hostname']
addHook({ name: 'url' }, function (url) {
shimmer.wrap(url, 'parse', (parse) => {
return function wrappedParse (input) {
const parsedValue = parse.apply(this, arguments)
if (!parseFinishedChannel.hasSubscribers) return parsedValue
parseFinishedChannel.publish({
input,
parsed: parsedValue,
isURL: false,
})
return parsedValue
}
})
const URLPrototype = url.URL.prototype.constructor.prototype
for (const property of instrumentedGetters) {
shimmer.wrap(URLPrototype, property, function (originalGet) {
return function get () {
const result = originalGet.call(this)
if (!urlGetterChannel.hasSubscribers) return result
const context = { urlObject: this, result, property }
urlGetterChannel.publish(context)
return context.result
}
})
}
shimmer.wrap(url, 'URL', (URL) => {
return class extends URL {
constructor (input, base) {
super(...arguments)
if (!parseFinishedChannel.hasSubscribers) return
parseFinishedChannel.publish({
input,
base,
parsed: this,
isURL: true,
})
}
static [Symbol.hasInstance] (instance) {
return instance instanceof URL
}
}
})
if (url.URL.parse) {
shimmer.wrap(url.URL, 'parse', (parse) => {
return function wrappedParse (input, base) {
const parsedValue = parse.apply(this, arguments)
if (!parseFinishedChannel.hasSubscribers) return parsedValue
parseFinishedChannel.publish({
input,
base,
parsed: parsedValue,
isURL: true,
})
return parsedValue
}
})
}
})