@@ -6,7 +6,6 @@ import { existsSync, readdirSync, readFileSync } from 'fs';
66import { join } from 'path' ;
77import { inspect } from 'util' ;
88import { expect } from 'vitest' ;
9- import WebSocket from 'ws' ;
109
1110const CLEANUP_STEPS = new Set < ( ) => void > ( ) ;
1211
@@ -131,23 +130,8 @@ function deferredPromise<T = void>(
131130
132131type Expected = Envelope | ( ( envelope : Envelope ) => void ) ;
133132
134- /** Drives Cloudflare Agents over the WebSocket protocol the Agents SDK speaks. */
135- type AgentRunner = {
136- /**
137- * Opens a chat WebSocket to `/agents/<binding>/<instance>`, sends one
138- * `cf_agent_use_chat_request` frame, and resolves once the turn completes.
139- */
140- sendChatMessage ( options : { binding : string ; instance : string ; prompt : string } ) : Promise < void > ;
141- /**
142- * Opens a WebSocket to `/agents/<binding>/<instance>`, sends one RPC frame,
143- * and resolves on the matching reply.
144- */
145- callRpc ( options : { binding : string ; instance : string ; method : string ; args : unknown [ ] } ) : Promise < void > ;
146- } ;
147-
148133type StartResult = {
149134 completed ( ) : Promise < void > ;
150- agents : AgentRunner ;
151135 makeRequest < T > (
152136 method : 'get' | 'post' ,
153137 path : string ,
@@ -428,107 +412,10 @@ export function createRunner(...paths: string[]) {
428412 reject ( e ) ;
429413 } ) ;
430414
431- async function getWorkerUrl ( ) : Promise < string > {
432- return `http://localhost:${ await workerPortPromise } ` ;
433- }
434-
435- /** Sends a single frame over a WS to the given agent instance and resolves once `predicate` matches a reply. */
436- async function driveAgentSocket (
437- binding : string ,
438- instance : string ,
439- frame : unknown ,
440- isDone : ( reply : { type ?: string ; id ?: string ; done ?: boolean } ) => boolean ,
441- timeoutLabel : string ,
442- ) : Promise < void > {
443- const baseUrl = await getWorkerUrl ( ) ;
444- const wsUrl = `${ baseUrl . replace ( / ^ h t t p / , 'ws' ) } /agents/${ binding } /${ instance } ` ;
445-
446- return new Promise < void > ( ( resolveSocket , rejectSocket ) => {
447- const socket = new WebSocket ( wsUrl ) ;
448- const timeout = setTimeout ( ( ) => {
449- socket . close ( ) ;
450- rejectSocket ( new Error ( `Timed out waiting for ${ timeoutLabel } ` ) ) ;
451- } , 10_000 ) ;
452-
453- socket . on ( 'open' , ( ) => {
454- socket . send ( JSON . stringify ( frame ) ) ;
455- } ) ;
456-
457- socket . on ( 'message' , data => {
458- try {
459- const parsed = JSON . parse ( data . toString ( ) ) as { type ?: string ; id ?: string ; done ?: boolean } ;
460- if ( isDone ( parsed ) ) {
461- clearTimeout ( timeout ) ;
462- socket . close ( ) ;
463- resolveSocket ( ) ;
464- }
465- } catch {
466- // Ignore non-JSON / unrelated frames.
467- }
468- } ) ;
469-
470- socket . on ( 'error' , err => {
471- clearTimeout ( timeout ) ;
472- rejectSocket ( err ) ;
473- } ) ;
474- } ) ;
475- }
476-
477415 return {
478416 completed : async function ( ) : Promise < void > {
479417 return isComplete ;
480418 } ,
481- agents : {
482- sendChatMessage : function ( {
483- binding,
484- instance,
485- prompt,
486- } : {
487- binding : string ;
488- instance : string ;
489- prompt : string ;
490- } ) : Promise < void > {
491- const id = `chat-${ instance } ` ;
492- const frame = {
493- type : 'cf_agent_use_chat_request' ,
494- id,
495- init : {
496- method : 'POST' ,
497- body : JSON . stringify ( {
498- messages : [ { id : 'msg-1' , role : 'user' , parts : [ { type : 'text' , text : prompt } ] } ] ,
499- } ) ,
500- } ,
501- } ;
502- return driveAgentSocket (
503- binding ,
504- instance ,
505- frame ,
506- reply => reply . type === 'cf_agent_use_chat_response' && reply . id === id && ! ! reply . done ,
507- 'chat response' ,
508- ) ;
509- } ,
510- callRpc : function ( {
511- binding,
512- instance,
513- method,
514- args,
515- } : {
516- binding : string ;
517- instance : string ;
518- method : string ;
519- args : unknown [ ] ;
520- } ) : Promise < void > {
521- const id = `rpc-${ method } ` ;
522- const frame = { type : 'rpc' , id, method, args } ;
523- return driveAgentSocket (
524- binding ,
525- instance ,
526- frame ,
527- reply => reply . type === 'rpc' && reply . id === id && ! ! reply . done ,
528- `RPC reply to "${ method } "` ,
529- ) ;
530- } ,
531- } ,
532419 makeRequest : async function < T > (
533420 method : 'get' | 'post' ,
534421 path : string ,
0 commit comments