Skip to content

Python library selection

This page is the include/exclude record for Python queues. Combined from two candidate lists: distributed task-queue frameworks, and a mixed in-process / broker-client / framework list.

This lab measures local handoff on one machine. Compare inside one language and one communication category (T / A, plus opt-in P / S / D). Brokers are category N and stay out of the published matrix. See Comparison rules and Queue categories.

Decision

Decision Libraries
Already in collections.deque (deque-lock), queue.Queue, asyncio.Queue, multiprocessing.Queue
Added queue.SimpleQueue, janus (async face only), multiprocessing.SimpleQueue (opt-in P)
Out — not a handoff queue Celery, RQ, Huey, Dramatiq, Taskiq, ARQ, Procrastinate, TaskTiger, WakaQ, Taskflow, APScheduler, Pydantic Job Queue / typed job runners, StreaQ, ArdiQ, Nameko, FastStream
Out — category N (localhost broker) pika, aio-pika, kombu, confluent-kafka, kafka-python / aiokafka, redis-py, boto3 (SQS), azure-servicebus, google-cloud-pubsub, nats-py, pyzmq

The advice to prefer broker clients (#6–16 on the second list) for “raw enqueue/dequeue” is a different experiment. A localhost Redis or RabbitMQ row is client + serialize + loopback + server. It must never share a chart with deque-lock.

In this lab

Log name Category Why
deque-lock T / locked collections.deque + Lock. Locked baseline. Already present.
queue.Queue T / concurrent Threading MPMC with maxsize, task_done, condvar. Already present.
queue.SimpleQueue T / concurrent Same module, different implementation: C-accelerated, unbounded, no task_done. The usual faster stdlib alternative. Added.
asyncio.Queue A Event-loop queue. Already present.
janus A Third-party async face of janus.Queue. Compared only to other A libraries. The hybrid thread↔async path is not a category and is not timed. Added.
spsc-ring / steal-deque T Harness families, not from the candidate lists. Already present.
multiprocessing.Queue P Stdlib IPC. Already present, opt-in.
multiprocessing.SimpleQueue P Unbounded pipe; no maxsize. Opt-in. Added.
shared-ring / sqlite-queue S / D Opt-in families, not from the candidate lists. Already present.

queue.LifoQueue and queue.PriorityQueue are the same module with different order. FIFO vs LIFO vs priority is a property, not a reason to rank them against FIFO queues.

Out: task-queue frameworks

These accept a callable (or a job envelope), persist it, retry it, and run a worker process. That is a scheduler, not a payload handoff. JavaScript p-queue is the same kind of object and lives under Other.

Library Why not
Celery Dominant distributed task framework. Broker + result backend + worker. DESIGN.md lists it out of T/A.
RQ Redis job queue. Needs Redis; times the job runner, not a queue primitive.
Huey Lightweight task queue (Redis/SQLite). Same job-runner semantics. SQLite-as-queue is already category D via sqlite-queue.
Dramatiq Celery alternative on RabbitMQ/Redis. Framework, not a handoff API.
Taskiq Async-first Celery/Dramatiq-style framework. Pluggable brokers.
ARQ asyncio Redis jobs. Broker + worker.
Procrastinate PostgreSQL job queue. Durable remote store, not local D.
TaskTiger Redis task processing with reliability features.
WakaQ Redis Celery alternative.
Taskflow Workflow/orchestration (OpenStack). Not a queue.
APScheduler Cron/interval scheduler. Same class as p-queue.
Pydantic Job Queue / typed queues Typed job runners (SAQ, PgQueuer, and similar). Still jobs + a backend.
StreaQ Async Redis queue. Category N.
ArdiQ Redis-backed modern queue. Category N.
Nameko Microservices/RPC on RabbitMQ. Not a handoff queue.
FastStream Async wrapper over Kafka/RabbitMQ/NATS/Redis. Broker framework.

In-memory or “eager” backends (Celery eager, Dramatiq StubBroker, Huey memory) still time dispatch/retry/serialization, not put/get.

Out: broker clients (category N)

These are the right objects for a later localhost system report. They are not T, A, P, S, or D.

Library Broker Why not now
pika RabbitMQ (AMQP) Local broker + framing.
aio-pika RabbitMQ Same, async client.
kombu AMQP / Redis / SQS Celery’s transport layer. Still a broker client.
confluent-kafka / kafka-python / aiokafka Kafka Needs a Kafka process.
redis (Lists/Streams) Redis / Valkey Ad-hoc queue on a server.
boto3 (SQS) AWS SQS Cloud service, not a local primitive.
azure-servicebus Azure Service Bus Same.
google-cloud-pubsub GCP Pub/Sub Same.
nats-py NATS Local NATS is still category N.
pyzmq ZeroMQ DESIGN.md lists ZeroMQ out of T/A.

Category N needs its own host requirements, payload serialization, and a report labeled “localhost”. It is unpublished on purpose.

Hybrid janus

janus exists to bridge a thread and an asyncio task on one queue. That path is useful in production and not a comparison category here (never rank T against A). The adapter uses only async_q, so the row is an A library: “what does janus cost versus asyncio.Queue when both faces are not in play?”