@@ -78,6 +78,10 @@ function startMockAnthropicServer() {
7878 const answersTool = req . body . messages . some (
7979 message => Array . isArray ( message . content ) && message . content . some ( block => block . type === 'tool_result' ) ,
8080 ) ;
81+ if ( mode === 'thread_stream_failed_signal_reuse' && ! answersTool ) {
82+ res . status ( 400 ) . json ( { type : 'error' , error : { type : 'invalid_request_error' , message : 'Bad thread' } } ) ;
83+ return ;
84+ }
8185 const message = reply ( mode , answersTool ? 'final' : 'tools' ) ;
8286
8387 if ( ! req . body . stream ) {
@@ -86,7 +90,7 @@ function startMockAnthropicServer() {
8690 }
8791
8892 res . writeHead ( 200 , { 'Content-Type' : 'text/event-stream' , 'Cache-Control' : 'no-cache' , Connection : 'keep-alive' } ) ;
89- // The body closes after the first text delta, without `message_stop`.
93+ // The body closes after the first tool input delta, without `message_stop`.
9094 const events = mode === 'thread_stream_truncated' ? streamEvents ( message ) . slice ( 0 , 3 ) : streamEvents ( message ) ;
9195 events . forEach ( ( event , index ) => {
9296 setTimeout ( ( ) => {
@@ -115,6 +119,17 @@ const tools = [
115119] ;
116120const params = { model : MODEL , max_tokens : 100 , messages : [ { role : 'user' , content : 'Weather in Vienna?' } ] } ;
117121
122+ async function streamFollowUp ( client , signal ) {
123+ const answer = { role : 'user' , content : [ { type : 'tool_result' , tool_use_id : 'toolu_1' , content : 'sunny' } ] } ;
124+ const followUp = await client . beta . messages . create (
125+ { ...params , messages : [ ...params . messages , answer ] , stream : true } ,
126+ { signal } ,
127+ ) ;
128+ for await ( const _event of followUp ) {
129+ // consume
130+ }
131+ }
132+
118133const MODES = {
119134 async runner_stream_eager ( client ) {
120135 for await ( const stream of client . beta . messages . toolRunner ( {
@@ -152,14 +167,12 @@ const MODES = {
152167 async thread_stream_signal_reuse ( client ) {
153168 const stream = client . beta . messages . thread ( { model : MODEL , max_tokens : 100 } ) . stream ( params . messages ) ;
154169 await stream . finalMessage ( ) ;
155- const answer = { role : 'user' , content : [ { type : 'tool_result' , tool_use_id : 'toolu_1' , content : 'sunny' } ] } ;
156- const followUp = await client . beta . messages . create (
157- { ...params , messages : [ ...params . messages , answer ] , stream : true } ,
158- { signal : stream . controller . signal } ,
159- ) ;
160- for await ( const _event of followUp ) {
161- // consume
162- }
170+ await streamFollowUp ( client , stream . controller . signal ) ;
171+ } ,
172+ async thread_stream_failed_signal_reuse ( client ) {
173+ const stream = client . beta . messages . thread ( { model : MODEL , max_tokens : 100 } ) . stream ( params . messages ) ;
174+ await stream . finalMessage ( ) . catch ( ( ) => { } ) ;
175+ await streamFollowUp ( client , stream . controller . signal ) ;
163176 } ,
164177 async thread_stream_abort ( client ) {
165178 const stream = client . beta . messages . thread ( { model : MODEL , max_tokens : 100 } ) . stream ( params . messages ) ;
0 commit comments