muffin/lib.rs
1//! Muffin is a background job processing library designed to work with MongoDB as its storage backend.
2//!
3//! *Requires MongoDB 6 with feature compatibility level set to `6`.*
4//!
5//! # Features
6//! - Asynchronous processing using [`Tokio`](https://docs.rs/tokio/latest/tokio/)
7//! - Job objects serialized with [`Serde`](https://docs.rs/serde/latest/serde/)
8//! - [`Scheduled jobs`](Muffin::schedule())
9//! - [`Prioritized jobs`](Job::priority())
10//! - Retries with [`custom backoff strategies`](Job::backoff())
11//! - [`Unique jobs`](Job::unique_key())
12//!
13//! # Example
14//!
15//! ```no_run
16//! use std::sync::Arc;
17//!
18//! use async_trait::async_trait;
19//! use mongodb::{bson::doc, Client};
20//! use muffin::{Job, ProcessResult, Muffin, Status};
21//! use serde::{Deserialize, Serialize};
22//!
23//! struct JobState {
24//! mongo_client: Client,
25//! }
26//!
27//! #[derive(Serialize, Deserialize)]
28//! struct MyJob {
29//! name: String,
30//! }
31//!
32//! #[async_trait]
33//! impl Job for MyJob {
34//! type State = Arc<JobState>;
35//!
36//! fn id() -> &'static str
37//! where
38//! Self: Sized,
39//! {
40//! // A unique identifier of the job
41//! "MyJob"
42//! }
43//!
44//! async fn process(&self, state: Self::State) -> ProcessResult {
45//! // Do something with self.name and state
46//! Ok(Status::Completed)
47//! }
48//! }
49//!
50//! #[tokio::main]
51//! async fn main() -> muffin::Result<()> {
52//! // Connect to a database called "muffin_testing".
53//! let client = Client::with_uri_str("mongodb://localhost:27017").await?;
54//! let database = client.database("muffin_testing");
55//!
56//! // The state is passed to each "process" method on an instance of Job.
57//! let state = JobState {
58//! mongo_client: client,
59//! };
60//! let mut muffin = Muffin::new(database, Arc::new(state)).await?;
61//!
62//! // Create a new job and push it for processing
63//! muffin
64//! .push(MyJob {
65//! name: "Peter".into(),
66//! })
67//! .await?;
68//!
69//! // Register jobs that should be processed.
70//! muffin.register::<MyJob>();
71//!
72//! // Start processing jobs.
73//! tokio::select! {
74//! _ = muffin.run() => {},
75//! _ = tokio::signal::ctrl_c() => {
76//! eprintln!("Received ctrl+c!");
77//! }
78//! };
79//!
80//! // Need to wait for all in-flight jobs to finish processing.
81//! muffin.shutdown().await;
82//!
83//! Ok(())
84//! }
85//!```
86//!
87//! You can find other examples in the [`repository`](https://github.com/jiripospisil/muffin/tree/master/examples).
88
89pub mod backoff;
90mod config;
91mod db;
92mod job;
93mod muffin;
94mod types;
95
96pub use crate::muffin::Muffin;
97pub use config::{Config, ConfigBuilder};
98pub use job::Job;
99pub use types::{Error, JobPersistedStatus, ProcessResult, Result, Schedule, Status};