Sazabi
CLI

Workflows

Automation patterns and workflows using the Sazabi CLI.

The Sazabi CLI is designed for automation. Every command supports --json for machine-readable output, making it easy to integrate Sazabi into scripts, CI/CD pipelines, and monitoring workflows.

Authentication for automation

For automated workflows, use API keys instead of interactive browser-based authentication.

Creating an API key

Create a secret key in the Sazabi dashboard:

  1. Go to Settings > API Keys
  2. Click Create API key and select Secret
  3. Copy the key and store it securely

Using API keys in scripts

Set the SAZABI_TOKEN environment variable:

export SAZABI_TOKEN="sazabi_secret_..."
sazabi projects list --json

Or pass the token directly per command:

sazabi projects list --token "sazabi_secret_..." --json

Secret keys provide full access to your organization. Store them in a secrets manager and never commit them to source control.

CI/CD integration

Deployment tracking

Track deployments by sending a message to Sazabi when your CI pipeline runs:

#!/bin/bash
set -e

# Send deployment notification to Sazabi
RESPONSE=$(sazabi messages send \
  "Deployment started: $SERVICE_NAME to $ENVIRONMENT at $(date -u +%Y-%m-%dT%H:%M:%SZ)" \
  --json)

THREAD_ID=$(echo "$RESPONSE" | jq -r '.threadId')
echo "Sazabi thread: $THREAD_ID"

# Run your deployment
deploy_application

# Follow up with status
sazabi messages send "Deployment completed successfully" \
  --thread-id "$THREAD_ID" \
  --json

Post-deployment log verification

After deploying, verify the application is logging correctly:

#!/bin/bash

# Start tailing logs in the background
sazabi logs tail --json --services "$SERVICE_NAME" > /tmp/deploy-logs.json &
TAIL_PID=$!

# Give the application time to start
sleep 30

# Stop tailing
kill $TAIL_PID 2>/dev/null || true

# Check for errors
ERROR_COUNT=$(grep -c '"severity":"ERROR"' /tmp/deploy-logs.json || echo "0")
if [ "$ERROR_COUNT" -gt 0 ]; then
  echo "Found $ERROR_COUNT errors after deployment"
  cat /tmp/deploy-logs.json | jq 'select(.severity == "ERROR")'
  exit 1
fi

echo "No errors detected"

GitHub Actions example

name: Deploy and Monitor

on:
  push:
    branches: [main]

jobs:
  deploy:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4

      - name: Install Sazabi CLI
        run: npm install -g @sazabi/cli

      - name: Notify deployment start
        env:
          SAZABI_TOKEN: ${{ secrets.SAZABI_TOKEN }}
        run: |
          RESPONSE=$(sazabi messages send \
            "Deploying ${{ github.repository }} commit ${{ github.sha }}" \
            --json)
          echo "THREAD_ID=$(echo $RESPONSE | jq -r '.threadId')" >> $GITHUB_ENV

      - name: Deploy application
        run: ./deploy.sh

      - name: Notify deployment complete
        env:
          SAZABI_TOKEN: ${{ secrets.SAZABI_TOKEN }}
        run: |
          sazabi messages send "Deployment complete" \
            --thread-id "${{ env.THREAD_ID }}" \
            --json

Log forwarding workflows

Forward application logs

Pipe application output directly to Sazabi:

# Forward stdout and stderr
./my-application 2>&1 | sazabi logs forward

# Forward from a log file
sazabi logs forward --file /var/log/app.log

# Follow a log file continuously
sazabi logs forward --file /var/log/app.log --follow

Batch log import

Import historical logs from a file:

# Import with default batch size (100)
sazabi logs forward --file application.log

# Adjust batch size for large files
sazabi logs forward --file large-application.log --batch-size 500

Docker container logs

Forward Docker container logs to Sazabi:

docker logs -f my-container 2>&1 | sazabi logs forward

Or in a docker-compose setup:

services:
  my-app:
    image: my-app:latest
    logging:
      driver: local

  log-forwarder:
    image: node:20
    command: >
      sh -c "npm install -g @sazabi/cli &&
             docker logs -f my-app 2>&1 | sazabi logs forward"
    environment:
      - SAZABI_TOKEN=${SAZABI_TOKEN}
    volumes:
      - /var/run/docker.sock:/var/run/docker.sock

Real-time monitoring

Tail logs with filters

Monitor specific services or severity levels in real-time:

# Watch for errors and warnings
sazabi logs tail --severities ERROR,WARN

# Filter by service
sazabi logs tail --services api-gateway,auth-service

# Filter by environment
sazabi logs tail --environments production

# Search for specific patterns
sazabi logs tail --search "timeout"

# Combine filters
sazabi logs tail --severities ERROR --services payment-service --environments production

Capture logs around an action

Capture logs that occur during a specific operation:

#!/bin/bash

# Start capturing logs
sazabi logs tail --json --severities ERROR,WARN > /tmp/captured.json &
TAIL_PID=$!

# Perform the operation you want to monitor
curl -X POST https://api.example.com/trigger-job

# Wait for logs to arrive
sleep 5

# Stop capturing
kill $TAIL_PID

# Analyze captured logs
echo "Captured logs:"
cat /tmp/captured.json | jq '.body'

Timed monitoring session

Run a monitoring session for a fixed duration:

# Monitor for 5 minutes
sazabi logs tail --duration 300 --severities ERROR,WARN

# With JSON output for later analysis
sazabi logs tail --duration 300 --json > monitoring-session.json

Scripted management

Project setup automation

Automate project configuration in a new environment:

#!/bin/bash
set -e

# List available organizations
ORG_ID=$(sazabi organizations list --json | jq -r '.organizations[0].id')
sazabi organizations use "$ORG_ID"

# List and select a project
PROJECT_ID=$(sazabi projects list --json | jq -r '.projects[] | select(.name == "production") | .id')
sazabi projects use "$PROJECT_ID"

# Create an API key for this environment
KEY_RESPONSE=$(sazabi public-keys create "CI Pipeline" --json)
PUBLIC_KEY=$(echo "$KEY_RESPONSE" | jq -r '.publicKey.value')

echo "Configuration complete"
echo "Public key: $PUBLIC_KEY"

Rotate API keys

Rotate API keys periodically:

#!/bin/bash
set -e

# Create new key
NEW_KEY=$(sazabi secret-keys create "Rotated $(date +%Y-%m-%d)" --json)
NEW_KEY_VALUE=$(echo "$NEW_KEY" | jq -r '.secretKey.value')
NEW_KEY_ID=$(echo "$NEW_KEY" | jq -r '.secretKey.id')

# Update your secrets manager with the new key
# update_secrets_manager "$NEW_KEY_VALUE"

# Delete old keys (keeping the new one)
sazabi secret-keys list --json | jq -r ".secretKeys[] | select(.id != \"$NEW_KEY_ID\") | .id" | while read OLD_KEY_ID; do
  sazabi secret-keys delete "$OLD_KEY_ID" --json
  echo "Deleted old key: $OLD_KEY_ID"
done

echo "Key rotation complete"

List data source connections

Audit your data source connections:

# List all connections
sazabi data-sources connections list --json | jq '.connections[] | {type, displayName, status}'

# Check for disconnected sources
sazabi data-sources connections list --json | jq '.connections[] | select(.status != "connected")'

Working with profiles

Profiles let you manage multiple contexts (organizations, projects, API endpoints) without re-authenticating.

Create environment profiles

# Create profiles for different environments
sazabi profiles create production
sazabi profiles create staging

# Authenticate each profile
sazabi auth login --profile production
sazabi auth login --profile staging

# Set the default project for each
sazabi projects use "$PROD_PROJECT_ID" --profile production
sazabi projects use "$STAGING_PROJECT_ID" --profile staging

Use profiles in scripts

# Query logs from production
sazabi logs tail --profile production --severities ERROR

# Send a message to staging
sazabi messages send "Running integration tests" --profile staging

Environment variable override

Set the profile via environment variable instead of flags:

export SAZABI_PROFILE=staging
sazabi logs tail --severities ERROR

Async message workflows

The CLI supports asynchronous message handling for long-running operations.

Send and wait for response

# Send a message and wait for the response
sazabi messages send "Analyze the last hour of error logs" --wait

# With a timeout (in milliseconds)
sazabi messages send "Summarize today's incidents" --wait --timeout 60000

Poll for completion

For longer operations, send the message and poll separately:

# Send the message
RESPONSE=$(sazabi messages send "Run comprehensive analysis" --json)
RUN_ID=$(echo "$RESPONSE" | jq -r '.runId')

# Poll until complete
sazabi runs get "$RUN_ID" --wait --json

Check run status

# Get current status
sazabi runs get "$RUN_ID" --json | jq '{status, response}'

Output formats

All commands support JSON output for scripting:

# Human-readable output (default)
sazabi projects list

# JSON output for scripts
sazabi projects list --json

# Parse with jq
sazabi projects list --json | jq '.projects[].name'

# Use in shell variables
PROJECT_COUNT=$(sazabi projects list --json | jq '.projects | length')

Next steps