eve
Version:
Filesystem-first framework for durable backend AI agents that run anywhere.
1 lines • 9.37 kB
JavaScript
import{contextStorage}from"#context/container.js";import{AuthKey,SessionKey}from"#context/keys.js";import{resolveTextToResponses}from"#channel/resolve-text.js";import{buildCallbackContext}from"#context/build-callback-context.js";import{buildApprovalResponseAuth,handleApprovalResponsePolicyError}from"#execution/tool-auth.js";import{getPendingInputBatches}from"#harness/pending-input-batches.js";import{clearPendingAuthorization,getAuthorizationResult,getPendingAuthorization,isAuthorizationSignal}from"#harness/authorization.js";import{createApprovalCandidate,expireApprovalCandidates,finishApprovalCandidate,getActiveApprovalCandidate,getApprovalAuditState,markApprovalCandidateAuthorizationRequired,settleAllowedCandidate,settleDirectApprovalResponse}from"#harness/approval-candidates.js";import{isApprovalRequest}from"#harness/input-request-class.js";const UNAUTHENTICATED_APPROVAL_FEEDBACK=`Authentication is required to respond to this approval.`;function shouldPrepareApprovalPolicyTools(e){let t=getPendingInputBatches(e.session.state),n=[...(e.stepInput?.attributedInputResponses??[]).map(({response:e})=>e),...e.stepInput?.inputResponses??[]];if(t.some(e=>e.requests.some(e=>isApprovalRequest(e)&&n.some(t=>t.requestId===e.requestId))))return!1;let r=e.now??Date.now();return getApprovalAuditState(e.session.state).activeCandidates.some(e=>e.expiresAt>r&&(e.status===`pending`||(e.authorizationChallenges?.some(e=>getAuthorizationResult(e.name)!==void 0)??!1)))}function shouldPrepareApprovalReplayTools(e){if(shouldPrepareApprovalPolicyTools(e))return!0;let t=getPendingInputBatches(e.session.state),n=[...(e.stepInput?.attributedInputResponses??[]).map(({response:e})=>e),...e.stepInput?.inputResponses??[]],r=t.length===1?t[0]:void 0;r!==void 0&&typeof e.stepInput?.message==`string`&&!n.some(e=>r.requests.some(t=>t.requestId===e.requestId))&&n.push(...resolveTextToResponses(e.stepInput.message,r.requests.filter(e=>!r.responseAuthRequiredRequestIds?.includes(e.requestId))));let i=new Set(n.filter(e=>e.optionId===`approve`).map(e=>e.requestId));return t.some(e=>e.requests.some(e=>isApprovalRequest(e)&&i.has(e.requestId)))}async function coordinateApprovalDelivery(e){let t=e.now??Date.now(),n=getApprovalAuditState(e.session.state).activeCandidates.filter(e=>e.expiresAt<=t).flatMap(e=>e.authorizationChallenges?.map(e=>e.name)??[]),r=expireApprovalCandidates({now:t,state:e.session.state}),i={...e.session,state:clearPendingAuthorization(r,n)},a=getApprovalAuditState(i.state),o=getPendingInputBatches(i.state),s=new Set(o.flatMap(e=>e.requests.map(e=>e.requestId))),c=a.settlements.filter(e=>s.has(e.requestId)),l=new Set(a.settlements.map(e=>e.requestId)),u=new Set([...l].filter(e=>!s.has(e))),d=hasResponseForRequest(e.stepInput,u),f=d?removeConsumedResponses(e.stepInput,u):e.stepInput;if(d&&c.length===0&&!hasMeaningfulInput(f))return deliveryResult(i,f,`park`);if(o.length===0)return deliveryResult(i,f);let p=f,m=new Set(o.flatMap(e=>e.responseAuthRequiredRequestIds??[])),h=o.flatMap(e=>e.requests),g=new Map(h.map(e=>[e.requestId,e])),_=[],v=[],y=new Set,b=!1,x=getApprovalAuditState(i.state).activeCandidates,S=[...p?.attributedInputResponses??[],...(p?.inputResponses??[]).map(e=>({auth:void 0,response:e}))];for(let{auth:e,response:n}of S){let r=g.get(n.requestId);if(r===void 0||!isApprovalRequest(r))continue;if(!m.has(n.requestId)){let r=contextStorage.getStore(),a=e===void 0?r?.get(AuthKey)??r?.get(SessionKey)?.auth.current??null:e;if(a!==null&&(n.optionId===`approve`||n.optionId===`cancel`)){let e=settleDirectApprovalResponse({actor:a,outcome:n.optionId===`approve`?`allowed`:`cancelled`,requestId:n.requestId,settledAt:t,state:i.state});i={...i,state:e.state},b||=e.changed}continue}if(y.add(n.requestId),n.optionId===`cancel`){let r=e===void 0?buildCallbackContext().session.auth.current:e;if(r===null){v.push(UNAUTHENTICATED_APPROVAL_FEEDBACK);continue}let a=settleDirectApprovalResponse({actor:r,outcome:`cancelled`,requestId:n.requestId,settledAt:t,state:i.state});i={...i,state:a.state},b||=a.changed;continue}if(n.optionId!==`approve`)continue;let a=e===void 0?buildCallbackContext().session.auth.current:e;if(a===null){v.push(UNAUTHENTICATED_APPROVAL_FEEDBACK);continue}let o=createApprovalCandidate({candidateIdPrefix:approvalCandidateIdPrefix(r.requestId,a),createdAt:t,expiresAt:t+6e5,requestId:r.requestId,responder:a,state:i.state});i={...i,state:o.state},b||=o.changed}let C=removeConsumedResponses(p,y);if(y.size>0)return deliveryResult(i,C,b?`continue-coordination`:`continue`,[],v);if(b)return deliveryResult(i,C,`continue`,[],v);let w=new Set(getPendingAuthorization(i.state)?.challenges.map(e=>e.name)??[]);for(let n of x){if(n.status===`authorization-required`){let e=n.authorizationChallenges??[];if(!e.some(e=>getAuthorizationResult(e.name)!==void 0)){_.push(...e.filter(e=>!w.has(e.name)));continue}}let r=g.get(n.requestId);if(r===void 0||getActiveApprovalCandidate(i.state,n.candidateId)===void 0)continue;let a=await authorizeCandidate({candidateId:n.candidateId,now:t,request:r,responder:n.responder,session:i,tools:e.tools});i=a.session,b||=a.didCommit,_.push(...a.challenges);let o=getApprovalAuditState(i.state).settlements.find(e=>e.requestId===n.requestId);o!==void 0&&c.push(o)}let T=appendSettledResponses(C,c);return c.length>0?deliveryResult(i,T,`continue`):b?deliveryResult(i,T,`continue-coordination`):deliveryResult(i,T,_.length>0?`authorization-required`:`continue`,_)}async function authorizeCandidate(e){let t={...e.session,state:expireApprovalCandidates({now:e.now,state:e.session.state})};if(getActiveApprovalCandidate(t.state,e.candidateId)===void 0)return{challenges:[],didCommit:!1,session:t};let n=e.tools.get(e.request.action.toolName)?.approval,r=n!==void 0&&typeof n!=`function`?n.response:void 0;if(r===void 0)return failCandidate({...e,reason:`Approval authorization is temporarily unavailable. Please try again.`,session:t});try{let n=buildCallbackContext(),i=await withAuthorizerTimeout(r({auth:buildApprovalResponseAuth({responder:e.responder,scope:e.candidateId}),request:{callId:e.request.action.callId,requestId:e.request.requestId,toolInput:e.request.action.input,toolName:e.request.action.toolName},response:{decision:`approve`},responder:e.responder,session:{id:n.session.id,initiator:n.session.auth.initiator,parent:n.session.parent,turn:n.session.turn}}));if(i.status===`rejected`)return t={...t,state:finishApprovalCandidate({candidateId:e.candidateId,completedAt:e.now,reason:i.reason,state:t.state,status:`rejected`})},{challenges:[],didCommit:!0,session:t};if(i.status!==`allowed`)return failCandidate({...e,session:t});let a=settleAllowedCandidate({candidateId:e.candidateId,settledAt:e.now,state:t.state});return{challenges:[],didCommit:a.changed,session:{...t,state:a.state}}}catch(n){let r=await handleApprovalResponsePolicyError(n).catch(()=>void 0);if(isAuthorizationSignal(r)){let n=r.challenges.map(e=>Date.parse(e.challenge.expiresAt??``)).filter(Number.isFinite).sort((e,t)=>e-t)[0];return t={...t,state:markApprovalCandidateAuthorizationRequired({authorizationChallenges:r.challenges.map(t=>({...t,candidateId:e.candidateId})),candidateId:e.candidateId,expiresAt:n,state:t.state})},{challenges:r.challenges.map(t=>({...t,candidateId:e.candidateId})),didCommit:!0,session:t}}return failCandidate({...e,session:t})}}function failCandidate(e){let t=e.reason??`We couldn’t verify your approval. Please try again.`;return{challenges:[],didCommit:!0,session:{...e.session,state:finishApprovalCandidate({candidateId:e.candidateId,completedAt:e.now,reason:t,state:e.session.state,status:`failed`})}}}function hasResponseForRequest(e,t){return e?.attributedInputResponses?.some(({response:e})=>t.has(e.requestId))===!0||e?.inputResponses?.some(e=>t.has(e.requestId))===!0}function hasMeaningfulInput(e){return e?.message!==void 0||(e?.attributedInputResponses?.length??0)>0||(e?.inputResponses?.length??0)>0||(e?.runtimeActionResults?.length??0)>0}function appendSettledResponses(e,t){if(t.length===0)return e;let n=new Set([...(e?.inputResponses??[]).map(e=>e.requestId),...(e?.attributedInputResponses??[]).map(({response:e})=>e.requestId)]),r=t.filter(e=>!n.has(e.requestId));return r.length===0?e:{...e,inputResponses:[...e?.inputResponses??[],...r.map(e=>({optionId:e.outcome===`allowed`?`approve`:`cancel`,requestId:e.requestId}))]}}function removeConsumedResponses(e,t){if(e===void 0)return;let n=(e.attributedInputResponses??[]).filter(({response:e})=>!t.has(e.requestId)),r=[...(e.inputResponses??[]).filter(e=>!t.has(e.requestId)),...n.map(({response:e})=>e)];return{...e,attributedInputResponses:void 0,inputResponses:r}}function deliveryResult(e,t,n=`continue`,r=[],i=[]){return{challenges:r,feedback:i,kind:n,session:e,stepInput:t}}function approvalCandidateIdPrefix(e,t){let n=[t.authenticator,t.issuer??``,t.principalType,t.principalId].join(`:`);return`${encodeCandidateIdPart(e)}.${encodeCandidateIdPart(n)}`}function encodeCandidateIdPart(e){return Array.from(e,e=>e.codePointAt(0).toString(36)).join(`-`)}async function withAuthorizerTimeout(e){let t;try{return await Promise.race([Promise.resolve(e),new Promise((e,n)=>{t=setTimeout(()=>n(Error(`Approval response authorizer timed out.`)),1e4)})])}finally{t!==void 0&&clearTimeout(t)}}export{coordinateApprovalDelivery,shouldPrepareApprovalPolicyTools,shouldPrepareApprovalReplayTools};