Motia Icon
Concepts

Logging & Debugging

Overview

Motia provides an out of the box logging and debugging system that works across different runtime environments. The system offers:

  • Real-time log streaming in both terminal and Motia Workbench
  • Multiple log levels with contextual information
  • Local development debugging tools
  • Integrated flow monitoring

Log Levels and Usage

Motia supports four standard log levels:

Log TypeDescription
infoGeneral information about step execution, flow progress, and successful operations
errorCritical issues, exceptions, failed operations, and system errors
debugDetailed debugging information and diagnostic data for troubleshooting
warnPotential issues, edge cases, or situations requiring attention

Example Usage

export const handler: StepHandler<typeof config> = async (input, { logger }) => {
  // Basic logging
  logger.info('Starting process')
 
  // Logging with context
  logger.info('Operation completed', {
    operationId: input.id,
    duration: 1500
  })
 
  // Error handling
  try {
    await riskyOperation()
  } catch (error) {
    logger.error('Operation failed', {
      error: error.message,
      stack: error.stack
    })
  }
 
  // Debug logging
  logger.debug('Operation details', {
    rawInput: input,
    timestamp: Date.now()
  })
 
  // Warning logging
  if (input.amount > 1000) {
    logger.warn('Large operation detected', {
      amount: input.amount,
      threshold: 1000
    })
  }
}

Running and Debugging

Start the Dev Server

  1. Navigate to your Motia project root folder
  2. Start the development server:
pnpm run dev
  1. You can monitor logs in two ways:
  • Open Motia Workbench, select your flow, and expand the logs container
  • View logs directly in the terminal where you ran the dev command

Trigger and Monitor Flows

You can trigger flows using either the CLI or an API step:

npx motia emit --topic <topic> --message '{}'

Debug Using Logs

Each log entry automatically includes:

  • timestamp: When the log was generated
  • traceId: Unique identifier for the flow execution
  • flows: Array of flow names this step belongs to
  • file: Source file generating the log
  • level: Log level
  • msg: Log message

Stopping the development server

Press Ctrl + C (or Cmd + C on macOS) in your terminal. That's it!

Best Practices

Structured Logging

// Good - Structured and searchable
logger.info('Payment processed', {
  paymentId: '123',
  amount: 100,
  status: 'success'
})
 
// Avoid - Harder to parse and search
logger.info(`Payment ${paymentId} processed: amount=${amount}`)

Performance Monitoring

export const handler: StepHandler<typeof config> = async (input, { logger }) => {
  const startTime = performance.now()
  
  // Process operation
  const result = await processOperation(input)
 
  logger.info('Operation completed', {
    duration: performance.now() - startTime,
    memoryUsage: process.memoryUsage().heapUsed
  })
}

Debugging Tips

  1. Add detailed context to error logs:
logger.error('Operation failed', {
  error: error.message,
  code: error.code,
  input: JSON.stringify(input),
  stack: error.stack
})
  1. Use debug logs for detailed troubleshooting:
logger.debug('Operation details', {
  rawInput: input,
  timestamp: Date.now(),
  state: currentState
})

Remember to stop your development server with Ctrl + C (or Cmd + C on macOS) when you're done debugging.

Need help? See our Community Resources for questions, examples, and discussions.

On this page