The function was ment to use the functional programming style, however, I forgot to uncomment and swap out the imperative style.
Example
This repository demonstrates modern, idiomatic Rust through two parts:
- Foundational Rust Examples – covering core concepts like lifetimes, error handling, async, and testing.
- Advanced Async Job Runner – a trait-based, concurrent task execution
framework built using
tokio
.
Part 1: Foundational Rust Examples
A lightweight collection of examples demonstrating essential Rust features,
without relying on external dependencies (except tokio
).
Concepts Covered
- Arrays and Iteration
- Lifetimes and Borrowing
- Error Handling with
Result
,?
, and custom messages - Async Programming using
#[tokio::main]
- File I/O with the standard library
- Unit and async testing
Key Functions
Function | Description |
---|---|
longest |
Returns the longest string in a slice without copying. |
read_and_parse |
Reads a file and parses its content into an integer. |
run_tasks |
Demonstrates spawning and awaiting async tasks. |
Testing
Includes both synchronous and asynchronous unit tests under a
#[cfg(test)]
module.
Part 2: Advanced Async Job Runner
An extensible, asynchronous job system using:
- Trait objects
- Pinned futures (
Pin<Box<dyn Future>>
) - Tokio’s
JoinSet
for concurrent execution - Fully dynamic job management without macros
Why It Matters
This system demonstrates:
- Manual implementation of async trait behavior (without
async_trait
) - Advanced type management (
Box<dyn Trait>
, lifetimes,Pin
) - Idiomatic use of
tokio::task::JoinSet
for parallelism
Architecture
Job
Trait
pub trait Job: Send + Sync {
fn name(&self) -> &str;
fn run<'a>(&self) -> Pin<Box<dyn Future<Output = JobResult> + Send + 'a>>
where Self: Sync + 'a;
}
JobRunner
Struct
pub struct JobRunner {
jobs: Vec<Box<dyn Job>>
}
Manages and runs jobs concurrently.
Built-In Jobs
Job Type | Behavior |
---|---|
FileJob |
(Planned) Reads from disk |
SleepJob |
Simulates a delay |
MathJob |
Performs a math task |
Usage
let mut runner = JobRunner::new();
runner.add_job(FileJob::new());
runner.add_job(SleepJob::new());
runner.add_job(MathJob::new());
for (name, result) in runner.run_all().await {
match result {
Ok(msg) => println!("{name}: {msg}"),
Err(err) => eprintln!("{name}: {err}"),
}
}
Testing & Extending
You can add unit or integration tests using mock jobs to simulate both success and failure.
Ideas for extension:
- Make the Jobs actually do something
- Interjob communication using channels
- Create a QueueRunner that will run jobs in sequence
- Create a ParallelRunner that will run jobs concurrently (simple rename)
- Create a system that allows QueueRunners and ParallelRunners to be combined
Requirements
- Rust 1.76+ (for full language support)
- Tokio 1.37+ (for async runtime)
Project Structure
src/
├── adv_async.rs # Advanced async JobRunner
├── basic.rs # Foundational examples
├── info.rs # Crate information from Cargo
├── lib.rs # Entry point for the library
Copyright & License
Copyright 2025 Jason Travis Smith
Licensed under the Apache License, Version 2.0 (the "License"); you may not use this library except in compliance with the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS" BASIS