@@ -209,6 +209,141 @@ describe("AnthropicHandler", () => {
209209 const requestOptions = mockCreate . mock . calls [ mockCreate . mock . calls . length - 1 ] ?. [ 1 ]
210210 expect ( requestOptions ?. headers ?. [ "anthropic-beta" ] ) . toContain ( "context-1m-2025-08-07" )
211211 } )
212+
213+ describe ( "advisor tool feature" , ( ) => {
214+ const systemPrompt = "You are a helpful assistant."
215+ const messages : Anthropic . Messages . MessageParam [ ] = [
216+ {
217+ role : "user" ,
218+ content : [ { type : "text" as const , text : "Hello" } ] ,
219+ } ,
220+ ]
221+
222+ it ( "should include advisor tool beta header when advisor tool is enabled" , async ( ) => {
223+ const advisorHandler = new AnthropicHandler ( {
224+ apiKey : "test-api-key" ,
225+ apiModelId : "claude-sonnet-4-6" ,
226+ anthropicAdvisorEnabled : true ,
227+ } )
228+
229+ const stream = advisorHandler . createMessage ( systemPrompt , messages )
230+
231+ for await ( const _chunk of stream ) {
232+ // Consume stream
233+ }
234+
235+ const requestOptions = mockCreate . mock . calls [ mockCreate . mock . calls . length - 1 ] ?. [ 1 ]
236+ expect ( requestOptions ?. headers ?. [ "anthropic-beta" ] ) . toContain ( "advisor-tool-2026-03-01" )
237+ } )
238+
239+ it ( "should inject advisor tool definition when advisor tool is enabled" , async ( ) => {
240+ const advisorHandler = new AnthropicHandler ( {
241+ apiKey : "test-api-key" ,
242+ apiModelId : "claude-sonnet-4-6" ,
243+ anthropicAdvisorEnabled : true ,
244+ } )
245+
246+ const stream = advisorHandler . createMessage ( systemPrompt , messages )
247+
248+ for await ( const _chunk of stream ) {
249+ // Consume stream
250+ }
251+
252+ const callArgs = mockCreate . mock . calls [ mockCreate . mock . calls . length - 1 ] ?. [ 0 ]
253+ expect ( callArgs ?. tools ) . toBeDefined ( )
254+ expect ( callArgs ?. tools ) . toEqual (
255+ expect . arrayContaining ( [
256+ expect . objectContaining ( {
257+ type : "advisor_20260301" ,
258+ name : "advisor" ,
259+ model : "claude-opus-4-6" ,
260+ } ) ,
261+ ] ) ,
262+ )
263+ } )
264+
265+ it ( "should include max_uses in advisor tool definition when configured" , async ( ) => {
266+ const customMaxUses = 5
267+ const advisorHandler = new AnthropicHandler ( {
268+ apiKey : "test-api-key" ,
269+ apiModelId : "claude-sonnet-4-6" ,
270+ anthropicAdvisorEnabled : true ,
271+ anthropicAdvisorMaxUses : customMaxUses ,
272+ } )
273+
274+ const stream = advisorHandler . createMessage ( systemPrompt , messages )
275+
276+ for await ( const _chunk of stream ) {
277+ // Consume stream
278+ }
279+
280+ const callArgs = mockCreate . mock . calls [ mockCreate . mock . calls . length - 1 ] ?. [ 0 ]
281+ const advisorTool = callArgs ?. tools ?. find ( ( tool : any ) => tool . type === "advisor_20260301" )
282+ expect ( advisorTool ) . toBeDefined ( )
283+ expect ( advisorTool ?. max_uses ) . toBe ( customMaxUses )
284+ } )
285+
286+ it ( "should use custom advisor model when configured" , async ( ) => {
287+ const customModel = "claude-opus-4-5-20251101"
288+ const advisorHandler = new AnthropicHandler ( {
289+ apiKey : "test-api-key" ,
290+ apiModelId : "claude-sonnet-4-6" ,
291+ anthropicAdvisorEnabled : true ,
292+ anthropicAdvisorModel : customModel ,
293+ } )
294+
295+ const stream = advisorHandler . createMessage ( systemPrompt , messages )
296+
297+ for await ( const _chunk of stream ) {
298+ // Consume stream
299+ }
300+
301+ const callArgs = mockCreate . mock . calls [ mockCreate . mock . calls . length - 1 ] ?. [ 0 ]
302+ const advisorTool = callArgs ?. tools ?. find ( ( tool : any ) => tool . type === "advisor_20260301" )
303+ expect ( advisorTool ) . toBeDefined ( )
304+ expect ( advisorTool ?. model ) . toBe ( customModel )
305+ } )
306+
307+ it ( "should not include advisor tool when advisor tool is disabled" , async ( ) => {
308+ const stream = handler . createMessage ( systemPrompt , messages )
309+
310+ for await ( const _chunk of stream ) {
311+ // Consume stream
312+ }
313+
314+ const callArgs = mockCreate . mock . calls [ mockCreate . mock . calls . length - 1 ] ?. [ 0 ]
315+ const advisorTool = callArgs ?. tools ?. find ( ( tool : any ) => tool . type === "advisor_20260301" )
316+ expect ( advisorTool ) . toBeUndefined ( )
317+
318+ // Also verify beta header is not present
319+ const requestOptions = mockCreate . mock . calls [ mockCreate . mock . calls . length - 1 ] ?. [ 1 ]
320+ const betaHeader = requestOptions ?. headers ?. [ "anthropic-beta" ]
321+ if ( betaHeader && typeof betaHeader === "string" ) {
322+ expect ( betaHeader ) . not . toContain ( "advisor-tool-2026-03-01" )
323+ }
324+ } )
325+
326+ it ( "should use default advisor model and max_uses when not configured" , async ( ) => {
327+ const advisorHandler = new AnthropicHandler ( {
328+ apiKey : "test-api-key" ,
329+ apiModelId : "claude-sonnet-4-6" ,
330+ anthropicAdvisorEnabled : true ,
331+ // No anthropicAdvisorModel or anthropicAdvisorMaxUses provided
332+ } )
333+
334+ const stream = advisorHandler . createMessage ( systemPrompt , messages )
335+
336+ for await ( const _chunk of stream ) {
337+ // Consume stream
338+ }
339+
340+ const callArgs = mockCreate . mock . calls [ mockCreate . mock . calls . length - 1 ] ?. [ 0 ]
341+ const advisorTool = callArgs ?. tools ?. find ( ( tool : any ) => tool . type === "advisor_20260301" )
342+ expect ( advisorTool ) . toBeDefined ( )
343+ expect ( advisorTool ?. model ) . toBe ( "claude-opus-4-6" ) // default
344+ expect ( advisorTool ?. max_uses ) . toBe ( 3 ) // default
345+ } )
346+ } )
212347 } )
213348
214349 describe ( "completePrompt" , ( ) => {
0 commit comments