DS DevShelfHub Projects · AI tools
Tutorials / CrewAI / Reference / Decorators / @persist
Decorator crewai.flow.persistence

@persist: Reference Guide

By DevShelfHub

Persists Flow state to a backend store (SQLite by default) so the flow can be resumed.

See the CrewAI API reference index, CrewAI introduction, hooks and events tutorial, and core concepts for surrounding context.

What is @persist?

@persist layers durable checkpoints underneath Flow execution. Applied at class scope, it captures Flow state so you can resume after process crashes, deploys, or human delays; applied at method scope, it snapshots after specific milestones such as finishing an expensive LLM call or receiving a webhook. The framework assigns a state identifier you thread back into kickoff to continue exactly where the graph left off.

SqliteProvider is the pragmatic default for single-region services, while JsonProvider or custom StorageBackend implementations help when compliance wants object-store artifacts or when you need cross-region replication. CheckpointConfig wires the backend alongside retention knobs — tune it when flows emit large intermediate payloads so databases do not grow without compaction policies.

Treat persisted state as part of your security boundary: it often includes prompts, tool outputs, and PII from human reviewers. Encrypt at rest where the backend allows, redact fields you do not need for resume, and expire checkpoints when tickets close so dormant sessions do not leak stale secrets.

When to Use

Long-running flows, HITL flows, anything that must survive a crash.

Use Cases

  • Long-running flows
  • HITL wait states
  • Distributed execution

Key Features

  • Class- or method-scoped
  • Pluggable storage
  • Automatic state IDs

When NOT to Use

Short, stateless tests where persistence adds noise.

Notes

Serialization constraints

State must round-trip through your provider. Open sockets, live clients, or ORM sessions belong outside persisted fields — store identifiers and rehydrate on resume.

Checkpoint growth

High-frequency persists on chatty loops inflate storage. Prefer persisting after coarse milestones or diff large blobs to object storage with references in Flow state.

Concurrency

Two workers resuming the same state ID can double-apply effects. Gate resumes with leases, version counters, or single-active-consumer queues at the orchestration layer.

Human-feedback pairing

Human gates may pause for hours. Persist before awaiting feedback so restarts do not replay paid LLM steps or duplicate outbound emails tied to the same ticket.

Import

python
from crewai.flow.persistence import persist

How to Apply

python
@persist()
class MyFlow(Flow[MyState]):
    ...

What It Enables

  • Resumability
  • Crash recovery
  • Long-running workflows

Code Examples

Whole-flow

python
@persist()
class MyFlow(Flow):
    @start()
    def begin(self):
        ...

Method-scoped checkpoint

python
class BillingFlow(Flow):
    @start()
    def load_invoice(self):
        return self.state.invoice_id

    @persist()
    @listen(load_invoice)
    def charge(self, invoice_id):
        return payments.charge(invoice_id)

JsonProvider with CheckpointConfig

python
from crewai.flow.flow import Flow, start
from crewai.state.checkpoint_config import CheckpointConfig, persist
from crewai.state import JsonProvider

@persist(config=CheckpointConfig(storage=JsonProvider()))
class AuditedFlow(Flow):
    @start()
    def begin(self):
        return 'checkpointed'

Integration Patterns

SqliteProvider (default)
JsonProvider
Custom StorageBackend

Common Mistakes

❌ Persisting an in-memory dict that contains unpicklable objects

✅ Use a Pydantic state model with serializable fields.

Related: Task class reference, Agent class reference, and the first Crew tutorial.

@persist FAQ

What is @persist in CrewAI?

Persists Flow state to a backend store (SQLite by default) so the flow can be resumed. @persist layers durable checkpoints underneath Flow execution. Applied at class scope, it captures Flow state so you can resume after process crashes, deploys, or human delays; applied at method scope, it snapshots after specific milestones such as finishing an expensive LLM call or receiving a webhook. The framework assigns a state identifier you thread back into kickoff to continue exactly where the graph left off. SqliteProvider is the pragmatic default for single-region …

Which module defines the CrewAI decorator @persist?

DevShelfHub maps @persist to Python module crewai.flow.persistence. Pin your installed crewai version and match imports to the import snippet on this page.

When should I use @persist?

Long-running flows, HITL flows, anything that must survive a crash.

When should I avoid @persist?

Short, stateless tests where persistence adds noise.

How do I apply @persist in Python?

@persist() class MyFlow(Flow[MyState]): ...

Where can I explore more CrewAI API reference pages?

Open the CrewAI API reference index on DevShelfHub to search classes, methods, and decorators, each with runnable examples, parameters, common mistakes, and cross-links.