Skip to content

Commit 608eba3

Browse files
committed
[DI] Probe file path matching algo should prefer shorter paths (#5186)
1 parent 9436b01 commit 608eba3

File tree

2 files changed

+32
-6
lines changed

2 files changed

+32
-6
lines changed

packages/dd-trace/src/debugger/devtools_client/state.js

+5-2
Original file line numberDiff line numberDiff line change
@@ -43,8 +43,8 @@ module.exports = {
4343
// If both are boundaries, or if characters match exactly
4444
if (isBoundary || urlChar === pathChar) {
4545
if (isBoundary) {
46-
lastBoundaryPos = matchLength
4746
atBoundary = true
47+
lastBoundaryPos = matchLength
4848
} else {
4949
atBoundary = false
5050
}
@@ -71,7 +71,10 @@ module.exports = {
7171
}
7272

7373
// If we found a valid match and it's better than our previous best
74-
if (atBoundary && lastBoundaryPos !== -1 && lastBoundaryPos > maxMatchLength) {
74+
if (atBoundary && (
75+
lastBoundaryPos > maxMatchLength ||
76+
(lastBoundaryPos === maxMatchLength && url.length < bestMatch[0].length) // Prefer shorter paths
77+
)) {
7578
maxMatchLength = lastBoundaryPos
7679
bestMatch[0] = url
7780
bestMatch[1] = scriptId

packages/dd-trace/test/debugger/devtools_client/state.spec.js

+27-4
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,13 @@ describe('findScriptFromPartialPath', function () {
2525
// Test case for when there's multiple partial matches
2626
listener({ params: { scriptId: 'should-match', url: 'file:///server/index.js' } })
2727
listener({ params: { scriptId: 'should-not-match', url: 'file:///index.js' } })
28+
29+
// Test case for when there's two equal length partial matches
30+
listener({ params: { scriptId: 'should-not-match-longest-a', url: 'file:///node_modules/foo/index.js' } })
31+
listener({ params: { scriptId: 'should-match-shortest-a', url: 'file:///foo/index.js' } })
32+
// The same, but in reverse order to ensure this doesn't influence the result
33+
listener({ params: { scriptId: 'should-match-shortest-b', url: 'file:///bar/index.js' } })
34+
listener({ params: { scriptId: 'should-not-match-longest-b', url: 'file:///node_modules/bar/index.js' } })
2835
}
2936
}
3037
}
@@ -117,14 +124,30 @@ describe('findScriptFromPartialPath', function () {
117124
const result = state.findScriptFromPartialPath('server/index.js')
118125
expect(result).to.deep.equal(['file:///server/index.js', 'should-match', undefined])
119126
})
127+
128+
it('should match the shorter of two equal length partial matches', function () {
129+
const result1 = state.findScriptFromPartialPath('foo/index.js')
130+
expect(result1).to.deep.equal(['file:///foo/index.js', 'should-match-shortest-a', undefined])
131+
132+
const result2 = state.findScriptFromPartialPath('bar/index.js')
133+
expect(result2).to.deep.equal(['file:///bar/index.js', 'should-match-shortest-b', undefined])
134+
})
120135
})
121136

122-
describe('circuit breakers', function () {
123-
it('should abort if the path is unknown', testPathNoMatch('this/path/does/not/exist.js'))
137+
describe('should abort if the path is', function () {
138+
it('unknown', testPathNoMatch('this/path/does/not/exist.js'))
139+
140+
it('undefined', testPathNoMatch(undefined))
141+
142+
it('an empty string', testPathNoMatch(''))
143+
144+
it('a slash', testPathNoMatch('/'))
145+
146+
it('a backslash', testPathNoMatch('\\'))
124147

125-
it('should abort if the path is undefined', testPathNoMatch(undefined))
148+
it('a Windows drive letter', testPathNoMatch('c:'))
126149

127-
it('should abort if the path is an empty string', testPathNoMatch(''))
150+
it('a Windows drive letter with a backslash', testPathNoMatch('c:\\'))
128151
})
129152

130153
function testPathNoMatch (path) {

0 commit comments

Comments
 (0)