type transformer = (arg: string) => any; interface IConfig { multiTransform?: boolean; } export async function call(tool: Tool, conf?: transformer | IConfig, ...transforms: transformer[]) { const config: IConfig = {} if (typeof conf === 'object') { Object.assign(config, conf) } else { transforms.unshift(conf as transformer) } const args = Deno.args; const shouldPair = transforms.length === args.length; const multiTransform = config.multiTransform || !shouldPair && transforms.length > 1; const transformedArgs = args.map((arg, i) => { if (shouldPair) return transforms[i](arg); if (multiTransform) return transforms.reduce((a, b) => b(a), arg) return transforms[0] ? transforms[0](arg) : arg }) await tool(...transformedArgs as T) } type prompt = [string, (v?: string) => boolean] | string export async function callWithArgPrompt(tool: Tool, prompts: prompt[]) { function buildPromptTransform(p: prompt): transformer { let validation = (v?: string) => !!v; let pText = p as string; if (Array.isArray(p)) { [pText, validation] = p; } return (a: string) => { while (!validation(a)) { a = prompt(pText) || '' } } } await call(tool, ...prompts.map(buildPromptTransform)) }