Execution Type Definitions
Complete type definitions for ExecutionStatus, ExecutionResult, ExecutionError, and execution state management
This document provides complete TypeScript type definitions for all execution-related types in the services-as-software platform.
Core Execution Types
ServiceExecution
The main execution type that tracks service execution.
// @errors: 7006
interface ServiceExecution extends Thing {
$type: 'ServiceExecution'
$id: string
order: ServiceOrder | string
service: Service | string
status: ExecutionStatus
// ^^^^^^^^^^^^^^^^^
progress: number
assignee?: ExecutionAssignee
result?: ExecutionResult
// ^^^^^^^^^^^^^^^
logs?: ExecutionLog[]
metrics?: ExecutionMetrics
error?: ExecutionError
// ^^^^^^^^^^^^^^
steps?: ExecutionStep[]
checkpoints?: ExecutionCheckpoint[]
priority?: ExecutionPriority
timeout?: number
retryPolicy?: RetryPolicy
webhooks?: Webhook[]
tags?: string[]
metadata?: ExecutionMetadata
}
const execution: ServiceExecution = {
// ^?
$type: 'ServiceExecution',
$id: 'exec-123',
order: 'order-456',
service: 'service-789',
status: 'running',
progress: 50,
}ExecutionStatus
Status enum for execution lifecycle.
type ExecutionStatus =
| 'queued' // Waiting to start
| 'starting' // Initializing execution
| 'running' // Currently executing
| 'paused' // Temporarily paused
| 'completed' // Successfully completed
| 'failed' // Execution failed
| 'cancelled' // Execution cancelled
| 'retry' // Retrying after failureState Transitions:
// Valid state transitions
const validTransitions: Record<ExecutionStatus, ExecutionStatus[]> = {
queued: ['starting', 'cancelled'],
starting: ['running', 'failed', 'cancelled'],
running: ['paused', 'completed', 'failed', 'cancelled'],
paused: ['running', 'cancelled'],
completed: [],
failed: ['retry', 'cancelled'],
cancelled: [],
retry: ['starting', 'failed'],
}
// Check if transition is valid
function isValidTransition(from: ExecutionStatus, to: ExecutionStatus): boolean {
return validTransitions[from].includes(to)
}Usage Example:
// @errors: 7006
// Create execution
const execution = await $.ServiceExecution.create({
order: orderId,
service: serviceId,
status: 'queued',
// ^?
progress: 0,
})
// Start execution
await $.ServiceExecution[execution.$id].start()
// Status: 'queued' -> 'starting' -> 'running'
// Pause execution
await $.ServiceExecution[execution.$id].pause()
// Status: 'running' -> 'paused'
// Resume execution
await $.ServiceExecution[execution.$id].resume()
// Status: 'paused' -> 'running'
// Complete execution
await $.ServiceExecution[execution.$id].complete(result)
// ^?
// Status: 'running' -> 'completed'ExecutionPriority
Priority levels for execution scheduling.
type ExecutionPriority =
| 'low' // Low priority, execute when resources available
| 'normal' // Normal priority (default)
| 'high' // High priority, execute soon
| 'urgent' // Urgent, execute immediatelyUsage Example:
// High priority execution
const urgentExecution = await $.ServiceExecution.create({
order: orderId,
service: serviceId,
status: 'queued',
priority: 'urgent',
})
// Query by priority
const highPriorityExecutions = await $.ServiceExecution.find({
status: 'queued',
priority: { $in: ['high', 'urgent'] },
})Execution Assignee
ExecutionAssignee
Who or what is executing the service.
interface ExecutionAssignee {
type: AssigneeType
id: string
name: string
model?: string
version?: string
capabilities?: string[]
}
type AssigneeType =
| 'ai-agent' // AI agent (Claude, GPT, etc.)
| 'human' // Human worker
| 'hybrid' // Combination of AI and human
| 'system' // System/automated processUsage Examples:
// @errors: 7006
// AI agent assignee
const aiAssignee: ExecutionAssignee = {
// ^?
type: 'ai-agent',
// ^^^^^^^^^^
id: 'claude-agent-1',
name: 'Claude SDR Agent',
model: 'claude-sonnet-4.5',
version: '2025-10-26',
capabilities: ['text-generation', 'analysis', 'reasoning'],
}
// Human assignee
const humanAssignee: ExecutionAssignee = {
type: 'human',
// ^^^^^^^
id: 'user-123',
name: 'Sarah Editor',
}
// Hybrid assignee
const hybridAssignee: ExecutionAssignee = {
type: 'hybrid',
id: 'content-team',
name: 'Content Team (AI + Human)',
}
// System assignee
const systemAssignee: ExecutionAssignee = {
type: 'system',
id: 'batch-processor',
name: 'Batch Processing System',
}Execution Result
ExecutionResult
Result of successful execution.
// @errors: 7006
interface ExecutionResult {
success: boolean
//^^^^^^^
output: any
summary: string
artifacts?: string[]
metadata?: Record<string, any>
}
const result: ExecutionResult = {
// ^?
success: true,
output: { emails_sent: 10 },
summary: 'Successfully sent 10 emails',
}Usage Examples:
// SDR outreach result
const sdrResult: ExecutionResult = {
success: true,
output: {
emails_sent: 10,
leads_contacted: 10,
bounce_rate: 0.1,
responses_received: 2,
meetings_booked: 1,
personalization_quality: 0.92,
},
summary: 'Successfully sent personalized outreach to 10 leads. 2 responses received, 1 meeting booked.',
artifacts: ['https://files.services.do/reports/campaign-123.pdf', 'https://files.services.do/data/campaign-123.csv'],
metadata: {
campaign_id: 'camp-123',
completion_time: '2025-10-26T14:30:00Z',
},
}
// Content generation result
const contentResult: ExecutionResult = {
success: true,
output: {
title: 'AI in Sales Automation: The Complete Guide',
word_count: 1547,
reading_time: 7,
seo_score: 95,
readability_score: 82,
},
summary: 'Generated 1,547-word blog post on AI in sales automation with SEO score of 95/100',
artifacts: ['https://files.services.do/content/blog-post-456.md', 'https://files.services.do/images/featured-456.jpg'],
}
// Data analysis result
const analysisResult: ExecutionResult = {
success: true,
output: {
insights: ['Sales increased 23% in Q3', 'Top product: Product A (45% of revenue)', 'Customer churn decreased to 5.2%'],
recommendations: ['Increase marketing spend on Product A', 'Launch customer retention program', 'Expand to new geographic markets'],
visualizations: ['revenue-trend-chart.png', 'product-mix-pie-chart.png', 'customer-cohort-heatmap.png'],
},
summary: 'Analyzed Q3 data and generated 3 key insights with actionable recommendations',
artifacts: ['https://dashboards.services.do/q3-analysis', 'https://files.services.do/reports/q3-executive-summary.pdf'],
}Execution Error
ExecutionError
Error information when execution fails.
// @errors: 7006
interface ExecutionError {
code: ErrorCode
// ^^^^^^^^^
message: string
stack?: string
step?: string
recoverable: boolean
//^^^^^^^^^^^
retryCount: number
context?: Record<string, any>
timestamp?: string
}
type ErrorCode =
// System Errors
| 'SYSTEM_ERROR'
| 'TIMEOUT'
| 'OUT_OF_MEMORY'
| 'RATE_LIMIT_EXCEEDED'
// Integration Errors
| 'API_ERROR'
| 'API_TIMEOUT'
// ^^^^^^^^^^^^^
| 'API_UNAUTHORIZED'
| 'API_RATE_LIMIT'
| 'INTEGRATION_ERROR'
| 'WEBHOOK_ERROR'
// Data Errors
| 'INVALID_INPUT'
| 'VALIDATION_ERROR'
| 'DATA_NOT_FOUND'
| 'DATABASE_ERROR'
// Service Errors
| 'SERVICE_UNAVAILABLE'
| 'DEPENDENCY_ERROR'
| 'CONFIGURATION_ERROR'
// Business Logic Errors
| 'BUSINESS_RULE_VIOLATION'
| 'PERMISSION_DENIED'
| 'QUOTA_EXCEEDED'
// AI/Model Errors
| 'MODEL_ERROR'
| 'GENERATION_FAILED'
| 'CONTENT_POLICY_VIOLATION'
// Custom Errors
| 'CUSTOM_ERROR'
const error: ExecutionError = {
// ^?
code: 'API_TIMEOUT',
message: 'API timeout after 30s',
recoverable: true,
retryCount: 1,
}Usage Examples:
// API timeout error
const apiTimeoutError: ExecutionError = {
code: 'API_TIMEOUT',
message: 'External API timeout after 30 seconds',
step: 'fetch-data',
recoverable: true,
retryCount: 1,
context: {
api: 'https://api.external.com/data',
timeout: 30000,
attempt: 1,
maxRetries: 3,
},
timestamp: '2025-10-26T10:30:35Z',
}
// Validation error
const validationError: ExecutionError = {
code: 'VALIDATION_ERROR',
message: 'Invalid email format for lead: john@invalid',
step: 'validate-leads',
recoverable: false,
retryCount: 0,
context: {
field: 'email',
value: 'john@invalid',
constraint: 'email-format',
},
}
// Rate limit error
const rateLimitError: ExecutionError = {
code: 'API_RATE_LIMIT',
message: 'LinkedIn API rate limit exceeded: 100 requests per hour',
step: 'linkedin-research',
recoverable: true,
retryCount: 0,
context: {
api: 'linkedin',
limit: 100,
period: '1h',
resetAt: '2025-10-26T11:00:00Z',
},
}
// Model error
const modelError: ExecutionError = {
code: 'MODEL_ERROR',
message: 'AI model returned empty response',
step: 'generate-content',
recoverable: true,
retryCount: 0,
context: {
model: 'claude-sonnet-4.5',
prompt_length: 1500,
max_tokens: 2000,
},
}Execution Logs
ExecutionLog
Log entry for execution events.
interface ExecutionLog {
timestamp: string
level: LogLevel
message: string
step?: string
context?: Record<string, any>
metadata?: LogMetadata
}
type LogLevel =
| 'debug' // Detailed debugging information
| 'info' // Informational messages
| 'warn' // Warning messages
| 'error' // Error messages
interface LogMetadata {
source?: string
component?: string
traceId?: string
spanId?: string
}Usage Examples:
// Info log
const infoLog: ExecutionLog = {
timestamp: '2025-10-26T10:30:00Z',
level: 'info',
message: 'Starting lead research',
step: 'research-lead',
context: {
lead_name: 'John Doe',
company: 'Acme Inc',
},
}
// Warn log
const warnLog: ExecutionLog = {
timestamp: '2025-10-26T10:30:15Z',
level: 'warn',
message: 'API response time exceeded threshold',
step: 'fetch-company-data',
context: {
api: 'clearbit',
response_time: 5500,
threshold: 5000,
},
}
// Error log
const errorLog: ExecutionLog = {
timestamp: '2025-10-26T10:30:35Z',
level: 'error',
message: 'Failed to send email',
step: 'send-email',
context: {
error_code: 'SMTP_ERROR',
smtp_response: '554 Transaction failed',
recipient: '[email protected]',
},
}
// Debug log
const debugLog: ExecutionLog = {
timestamp: '2025-10-26T10:30:05Z',
level: 'debug',
message: 'AI model request',
step: 'generate-message',
context: {
model: 'claude-sonnet-4.5',
prompt_tokens: 150,
max_tokens: 500,
},
metadata: {
traceId: 'trace-abc123',
spanId: 'span-def456',
},
}Execution Metrics
ExecutionMetrics
Performance metrics for execution.
interface ExecutionMetrics {
// Timing
startedAt?: string
completedAt?: string
duration?: number
// AI Usage
tokensUsed?: number
promptTokens?: number
completionTokens?: number
modelCalls?: number
// Costs
cost?: number
costBreakdown?: CostBreakdown
// API Usage
apiCalls?: number
apiCallsByService?: Record<string, number>
// Retries
retries?: number
retryDuration?: number
// Steps
stepsCompleted: number
stepsTotal: number
stepDurations?: Record<string, number>
// Quality
qualityScore?: number
errorRate?: number
// Custom metrics
custom?: Record<string, number>
}
interface CostBreakdown {
ai: number
apis: number
compute: number
storage: number
other: number
}Usage Examples:
// SDR execution metrics
const sdrMetrics: ExecutionMetrics = {
startedAt: '2025-10-26T10:00:00Z',
completedAt: '2025-10-26T10:05:30Z',
duration: 330000,
tokensUsed: 15000,
promptTokens: 8000,
completionTokens: 7000,
modelCalls: 10,
cost: 0.12,
costBreakdown: {
ai: 0.1,
apis: 0.02,
compute: 0,
storage: 0,
other: 0,
},
apiCalls: 25,
apiCallsByService: {
linkedin: 10,
clearbit: 10,
sendgrid: 5,
},
retries: 1,
retryDuration: 2000,
stepsCompleted: 30,
stepsTotal: 30,
stepDurations: {
'research-lead': 45000,
'craft-message': 30000,
'send-email': 5000,
},
qualityScore: 0.92,
errorRate: 0.1,
}
// Content generation metrics
const contentMetrics: ExecutionMetrics = {
startedAt: '2025-10-26T11:00:00Z',
completedAt: '2025-10-26T11:03:45Z',
duration: 225000,
tokensUsed: 3500,
promptTokens: 500,
completionTokens: 3000,
modelCalls: 4,
cost: 0.05,
costBreakdown: {
ai: 0.05,
apis: 0,
compute: 0,
storage: 0,
other: 0,
},
apiCalls: 0,
retries: 0,
stepsCompleted: 4,
stepsTotal: 4,
qualityScore: 0.95,
}Execution Steps
ExecutionStep
Individual workflow step tracking.
interface ExecutionStep {
id: string
name: string
status: StepStatus
startedAt?: string
completedAt?: string
duration?: number
assignee?: ExecutionAssignee
input?: any
output?: any
error?: ExecutionError
retries?: number
metadata?: Record<string, any>
}
type StepStatus =
| 'pending' // Not yet started
| 'running' // Currently executing
| 'completed' // Successfully completed
| 'failed' // Execution failed
| 'skipped' // Skipped (conditional logic)Usage Examples:
// Research step
const researchStep: ExecutionStep = {
id: 'research-lead-1',
name: 'Research John Doe at Acme Inc',
status: 'completed',
startedAt: '2025-10-26T10:00:00Z',
completedAt: '2025-10-26T10:00:45Z',
duration: 45000,
assignee: {
type: 'ai-agent',
id: 'claude-agent-1',
name: 'Claude Research Agent',
model: 'claude-sonnet-4.5',
},
input: {
lead: {
name: 'John Doe',
title: 'VP Sales',
company: 'Acme Inc',
linkedin: 'https://linkedin.com/in/johndoe',
},
},
output: {
talking_points: ['Acme recently raised $50M Series B', 'Expanding sales team by 50%', 'Using legacy CRM system'],
pain_points: ['Manual sales processes', 'Low team productivity', 'Difficulty tracking pipeline'],
},
metadata: {
tokens_used: 1200,
cost: 0.01,
},
}
// Failed step with error
const failedStep: ExecutionStep = {
id: 'send-email-1',
name: 'Send email to John Doe',
status: 'failed',
startedAt: '2025-10-26T10:02:00Z',
completedAt: '2025-10-26T10:02:05Z',
duration: 5000,
assignee: {
type: 'system',
id: 'email-service',
name: 'Email Service',
},
input: {
to: '[email protected]',
subject: 'Quick question about your sales process',
body: '...',
},
error: {
code: 'API_ERROR',
message: 'SMTP server returned 554 error',
recoverable: true,
retryCount: 0,
context: {
smtp_code: 554,
smtp_message: 'Transaction failed',
},
},
retries: 1,
}Execution Checkpoints
ExecutionCheckpoint
Checkpoint for pausing/resuming long-running executions.
interface ExecutionCheckpoint {
id: string
timestamp: string
step: string
state: ExecutionState
metadata?: Record<string, any>
}
interface ExecutionState {
currentStep: number
totalSteps: number
completedSteps: string[]
pendingSteps: string[]
variables: Record<string, any>
results: Record<string, any>
}Usage Example:
// Create checkpoint
const checkpoint: ExecutionCheckpoint = {
id: 'checkpoint-1',
timestamp: '2025-10-26T10:15:00Z',
step: 'process-batch',
state: {
currentStep: 250,
totalSteps: 1000,
completedSteps: ['step-1', 'step-2' /* ... */, , 'step-250'],
pendingSteps: ['step-251', 'step-252' /* ... */, , 'step-1000'],
variables: {
batch_size: 10,
processed_count: 250,
error_count: 5,
},
results: {
successful_items: 245,
failed_items: 5,
},
},
metadata: {
memory_usage: 256000000,
cpu_usage: 45.2,
},
}
// Resume from checkpoint
async function resumeExecution(execution: ServiceExecution, checkpoint: ExecutionCheckpoint): Promise<void> {
// Restore state
const state = checkpoint.state
// Continue from last completed step
for (const stepId of state.pendingSteps) {
await executeStep(execution, stepId, state.variables)
}
}Retry Policy
RetryPolicy
Configuration for automatic retry on failures.
interface RetryPolicy {
maxRetries: number
backoff: BackoffStrategy
initialDelay: number
maxDelay: number
retryableErrors?: ErrorCode[]
jitter?: boolean
}
type BackoffStrategy =
| 'linear' // Fixed delay
| 'exponential' // Exponentially increasing delay
| 'fibonacci' // Fibonacci sequence delayUsage Examples:
// Exponential backoff with jitter
const exponentialPolicy: RetryPolicy = {
maxRetries: 3,
backoff: 'exponential',
initialDelay: 1000,
maxDelay: 60000,
jitter: true,
retryableErrors: ['API_TIMEOUT', 'API_RATE_LIMIT', 'SERVICE_UNAVAILABLE'],
}
// Calculate retry delay
function calculateRetryDelay(attempt: number, policy: RetryPolicy): number {
let delay: number
switch (policy.backoff) {
case 'linear':
delay = policy.initialDelay
break
case 'exponential':
delay = policy.initialDelay * Math.pow(2, attempt)
break
case 'fibonacci':
delay = policy.initialDelay * fibonacci(attempt)
break
}
// Cap at max delay
delay = Math.min(delay, policy.maxDelay)
// Add jitter
if (policy.jitter) {
delay = delay * (0.5 + Math.random() * 0.5)
}
return delay
}
// Example retry delays (exponential with jitter)
// Attempt 1: ~1000ms (1s)
// Attempt 2: ~2000ms (2s)
// Attempt 3: ~4000ms (4s)Webhooks
Webhook
Webhook configuration for execution events.
interface Webhook {
url: string
events: WebhookEvent[]
headers?: Record<string, string>
retries?: number
timeout?: number
secret?: string
}
type WebhookEvent =
| 'execution.created'
| 'execution.started'
| 'execution.progress'
| 'execution.paused'
| 'execution.resumed'
| 'execution.completed'
| 'execution.failed'
| 'execution.cancelled'
| 'execution.step.started'
| 'execution.step.completed'
| 'execution.step.failed'Usage Example:
// Configure webhooks
const webhooks: Webhook[] = [
{
url: 'https://api.example.com/webhooks/execution',
events: ['execution.started', 'execution.completed', 'execution.failed'],
headers: {
Authorization: 'Bearer token123',
'X-Webhook-Secret': 'secret456',
},
retries: 3,
timeout: 5000,
},
{
url: 'https://slack.com/api/webhooks/abc123',
events: ['execution.completed', 'execution.failed'],
},
]
// Webhook payload
interface WebhookPayload {
event: WebhookEvent
timestamp: string
execution: {
id: string
status: ExecutionStatus
progress: number
result?: ExecutionResult
error?: ExecutionError
}
signature?: string
}Utility Types
ExecutionWithRelations
Execution with all relations populated.
interface ExecutionWithRelations extends ServiceExecution {
order: ServiceOrder
service: Service
workflow: BusinessWorkflow
customer: Person | Organization
}PartialExecution
Partial execution type for updates.
type PartialExecution = Partial<Omit<ServiceExecution, '$type' | '$id' | 'order' | 'service'>>ExecutionSummary
Lightweight execution summary.
interface ExecutionSummary {
id: string
status: ExecutionStatus
progress: number
startedAt?: string
completedAt?: string
duration?: number
success: boolean
}Type Guards
function isExecutionComplete(execution: ServiceExecution): boolean {
return execution.status === 'completed'
}
function isExecutionFailed(execution: ServiceExecution): boolean {
return execution.status === 'failed'
}
function isExecutionRunning(execution: ServiceExecution): boolean {
return ['starting', 'running'].includes(execution.status)
}
function canRetry(execution: ServiceExecution): boolean {
return (
execution.status === 'failed' &&
execution.error?.recoverable === true &&
execution.retryPolicy &&
execution.error.retryCount < execution.retryPolicy.maxRetries
)
}Complete Example
// Complete execution lifecycle
const execution: ServiceExecution = {
$type: 'ServiceExecution',
$id: 'exec-123',
order: 'order-456',
service: 'service-789',
status: 'completed',
progress: 100,
assignee: {
type: 'ai-agent',
id: 'claude-agent-1',
name: 'Claude SDR Agent',
model: 'claude-sonnet-4.5',
},
result: {
success: true,
output: {
emails_sent: 10,
responses_received: 2,
meetings_booked: 1,
},
summary: 'Successfully sent personalized outreach to 10 leads',
artifacts: ['https://files.services.do/reports/campaign-123.pdf'],
},
logs: [
{
timestamp: '2025-10-26T10:00:00Z',
level: 'info',
message: 'Starting execution',
},
// ... more logs
],
metrics: {
startedAt: '2025-10-26T10:00:00Z',
completedAt: '2025-10-26T10:05:30Z',
duration: 330000,
tokensUsed: 15000,
cost: 0.12,
apiCalls: 25,
retries: 1,
stepsCompleted: 30,
stepsTotal: 30,
qualityScore: 0.92,
},
steps: [
{
id: 'research-lead-1',
name: 'Research John Doe',
status: 'completed',
startedAt: '2025-10-26T10:00:00Z',
completedAt: '2025-10-26T10:00:45Z',
duration: 45000,
},
// ... more steps
],
priority: 'normal',
timeout: 3600000,
retryPolicy: {
maxRetries: 3,
backoff: 'exponential',
initialDelay: 1000,
maxDelay: 60000,
},
tags: ['production', 'ai-powered'],
metadata: {
createdAt: '2025-10-26T10:00:00Z',
updatedAt: '2025-10-26T10:05:30Z',
startedAt: '2025-10-26T10:00:00Z',
completedAt: '2025-10-26T10:05:30Z',
environment: 'production',
version: '1.0.0',
},
}See Also
- ServiceExecution API - Execution API reference
- Service Types - Service type definitions
- ServiceOrder API - Order API reference