Skip to content

Commit 5f5bec3

Browse files
sabrennerwatson
authored andcommitted
chore(llmobs): add internal ability to tag tool id on tool messages (#6022)
* add ability to tag tool id on tool messages * add type doc * fix test * remove documenting
1 parent dc1f6ef commit 5f5bec3

File tree

2 files changed

+59
-1
lines changed

2 files changed

+59
-1
lines changed

packages/dd-trace/src/llmobs/tagger.js

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -281,14 +281,15 @@ class LLMObsTagger {
281281

282282
const { content = '', role } = message
283283
const toolCalls = message.toolCalls
284+
const toolId = message.toolId
284285
const messageObj = { content }
285286

286287
const valid = typeof content === 'string'
287288
if (!valid) {
288289
this.#handleFailure('Message content must be a string.', 'invalid_io_messages')
289290
}
290291

291-
const condition = this.#tagConditionalString(role, 'Message role', messageObj, 'role')
292+
let condition = this.#tagConditionalString(role, 'Message role', messageObj, 'role')
292293

293294
if (toolCalls) {
294295
const filteredToolCalls = this.#filterToolCalls(toolCalls)
@@ -298,6 +299,14 @@ class LLMObsTagger {
298299
}
299300
}
300301

302+
if (toolId) {
303+
if (role === 'tool') {
304+
condition = this.#tagConditionalString(toolId, 'Tool ID', messageObj, 'tool_id')
305+
} else {
306+
log.warn(`Tool ID for tool message not associated with a "tool" role, instead got "${role}"`)
307+
}
308+
}
309+
301310
if (valid && condition) {
302311
messages.push(messageObj)
303312
}

packages/dd-trace/test/llmobs/tagger.spec.js

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -391,6 +391,44 @@ describe('tagger', () => {
391391
expect(() => tagger.tagLLMIO(span, messages, undefined)).to.throw()
392392
})
393393
})
394+
395+
describe('tool message tagging', () => {
396+
it('tags a span with a tool message', () => {
397+
const messages = [
398+
{ role: 'tool', content: 'The weather in San Francisco is sunny', toolId: '123' }
399+
]
400+
401+
tagger._register(span)
402+
tagger.tagLLMIO(span, messages, undefined)
403+
expect(Tagger.tagMap.get(span)).to.deep.equal({
404+
'_ml_obs.meta.input.messages': [
405+
{ role: 'tool', content: 'The weather in San Francisco is sunny', tool_id: '123' }
406+
]
407+
})
408+
})
409+
410+
it('throws if the tool id is not a string', () => {
411+
const messages = [
412+
{ role: 'tool', content: 'The weather in San Francisco is sunny', toolId: 123 }
413+
]
414+
415+
expect(() => tagger.tagLLMIO(span, messages, undefined)).to.throw()
416+
})
417+
418+
it('logs a warning if the tool id is not associated with a tool role', () => {
419+
const messages = [
420+
{ role: 'user', content: 'The weather in San Francisco is sunny', toolId: '123' }
421+
]
422+
423+
tagger._register(span)
424+
tagger.tagLLMIO(span, messages, undefined)
425+
426+
const messageTags = Tagger.tagMap.get(span)['_ml_obs.meta.input.messages']
427+
expect(messageTags[0]).to.not.have.property('tool_id')
428+
429+
expect(logger.warn).to.have.been.calledOnce
430+
})
431+
})
394432
})
395433

396434
describe('tagEmbeddingIO', () => {
@@ -640,6 +678,17 @@ describe('tagger', () => {
640678
expect(logger.warn.callCount).to.equal(5) // 4 for tool call + 1 for role
641679
})
642680
})
681+
682+
it('logs a warning if the tool id is not a string', () => {
683+
const messages = [
684+
{ role: 'tool', content: 'The weather in San Francisco is sunny', toolId: 123 }
685+
]
686+
687+
tagger._register(span)
688+
tagger.tagLLMIO(span, messages, undefined)
689+
expect(Tagger.tagMap.get(span)).to.not.have.property('_ml_obs.meta.input.messages')
690+
expect(logger.warn).to.have.been.calledOnce
691+
})
643692
})
644693
})
645694
})

0 commit comments

Comments
 (0)