tasker_pgmq/lib.rs
1//! # tasker-pgmq
2//!
3//! Generic `PostgreSQL` LISTEN/NOTIFY integration for PGMQ queues.
4//!
5//! This crate provides event-driven capabilities for PGMQ queue operations,
6//! enabling real-time notifications for queue creation, message enqueueing,
7//! and other queue lifecycle events.
8//!
9//! ## Features
10//!
11//! - **Generic Design**: Works with any PGMQ setup, not tied to specific applications
12//! - **Namespace Awareness**: Supports namespace extraction from queue names
13//! - **Reliable Notifications**: Built on `sqlx::PgListener` with auto-reconnection
14//! - **Minimal Payloads**: Keeps notifications under `pg_notify` 8KB limit
15//! - **Configurable Channels**: Customizable channel naming and prefixes
16//!
17//! ## Architecture
18//!
19//! The crate provides three main components:
20//!
21//! 1. **Event Types**: Structured representations of PGMQ events
22//! 2. **Database Triggers**: Automatically publish notifications via SQL triggers (recommended)
23//! 3. **Listeners**: Subscribe to and receive typed events via `pg_notify`
24//! 4. **Enhanced Client**: PGMQ wrapper that integrates with trigger-based notifications
25//!
26//! ## Usage - Trigger-Based (Recommended)
27//!
28//! ```rust,ignore
29//! use tasker_pgmq::{PgmqNotifyClient, PgmqNotifyListener, PgmqNotifyConfig, PgmqNotifyEvent};
30//!
31//! // 1. Install database triggers via migration (one-time setup)
32//! // Run: tasker-pgmq-cli generate-migration --name pgmq_notifications
33//! // Then apply the generated migration to your database
34//!
35//! // 2. Create enhanced PGMQ client with trigger-based notifications
36//! let config = PgmqNotifyConfig::new()
37//! .with_queue_naming_pattern(r"(?P<namespace>\w+)_queue")
38//! .with_default_namespace("orders");
39//!
40//! let mut client = PgmqNotifyClient::new(database_url, config).await?;
41//!
42//! // 3. Create listener for real-time event processing (TAS-51: bounded channel)
43//! let buffer_size = 1000; // From config.mpsc_channels.*.event_listeners.pgmq_event_buffer_size
44//! let mut listener = PgmqNotifyListener::new(pool, config, buffer_size).await?;
45//! listener.connect().await?;
46//! listener.listen_message_ready_for_namespace("orders").await?;
47//!
48//! // 4. Queue operations automatically emit notifications via triggers
49//! client.create_queue("orders_queue").await?; // Triggers queue_created notification
50//! client.send("orders_queue", &my_message).await?; // Triggers message_ready notification
51//!
52//! // 5. Process real-time events
53//! while let Some(event) = listener.next_event().await? {
54//! match event {
55//! PgmqNotifyEvent::MessageReady { msg_id, queue_name, .. } => {
56//! println!("Message {} ready in queue {}", msg_id, queue_name);
57//! // Process message with <10ms latency
58//! }
59//! }
60//! }
61//! ```
62
63pub(crate) mod channel_metrics;
64pub(crate) mod client;
65pub(crate) mod config;
66pub(crate) mod emitter;
67pub mod error;
68pub(crate) mod events;
69pub mod listener;
70pub mod types;
71
72// Re-export main types for trigger-based usage (recommended)
73pub use client::{PgmqClient, PgmqNotifyClient, PgmqNotifyClientFactory};
74pub use config::PgmqNotifyConfig;
75pub use error::{PgmqNotifyError, Result};
76pub use events::{
77 BatchReadyEvent, MessageReadyEvent, MessageWithPayloadEvent, PgmqNotifyEvent, QueueCreatedEvent,
78};
79pub use listener::PgmqNotifyListener;
80pub use types::{ClientStatus, MessagingError, QueueMetrics};
81
82// Legacy application-level emitters (for advanced use cases only)
83// Most users should use database triggers instead
84pub use emitter::{DbEmitter, NoopEmitter, PgmqNotifyEmitter};