Skip to content

pimalaya/io-time

I/O Time Documentation Matrix

I/O-free time library written in Rust, based on io-socket.

This library allows you to manage timers using an I/O-agnostic approach, based on 3 concepts:

Coroutine

A coroutine is an I/O-free, resumable and composable state machine that emits I/O requests. A coroutine is considered terminated when it does not emit I/O requests anymore.

See available coroutines at ./src/coroutines.

Runtime

A runtime contains all the I/O logic, and is responsible for processing I/O requests emitted by coroutines.

See available runtimes at ./src/runtimes.

Loop

The loop is the glue between coroutines and runtimes. It makes the coroutine progress while allowing the runtime to process I/O.

Features

TimeNow, TimeSleep, and TimeSleepUntil are always available as the core of the crate.

Default: timer + std.

Examples

Standard blocking client using TCP

use std::net::TcpStream;

use io_socket::runtimes::std::handle as socket_handle;
use io_time::coroutines::client::{TimerRequestSend, TimerRequestSendResult};

let mut stream = TcpStream::connect("localhost:1234").unwrap();

let mut arg = None;
let mut client = TimerRequestSend::start();

loop {
    match client.resume(arg.take()) {
        TimerRequestSendResult::Ok { .. } => break,
        TimerRequestSendResult::Io { input } => arg = Some(socket_handle(&mut stream, input).unwrap()),
        TimerRequestSendResult::Err { err } => panic!("{err}"),
    }
}

Standard blocking server using Unix sockets

use std::os::unix::net::UnixListener;

use io_socket::runtimes::std::handle as socket_handle;
use io_time::{
    coroutines::server::{TimerRequestHandle, TimerRequestHandleArg, TimerRequestHandleResult},
    runtimes::std::handle as time_handle,
    timer::{Timer, TimerConfig},
};

let mut timer = Timer::new(TimerConfig { /* … */ });
let listener = UnixListener::bind("/tmp/timer.sock").unwrap();
let (mut stream, _) = listener.accept().unwrap();

let mut server = TimerRequestHandle::new();
let mut arg: Option<TimerRequestHandleArg> = None;

loop {
    match server.resume(&mut timer, arg.take()) {
        TimerRequestHandleResult::Ok { events } => { /* handle events */ break }
        TimerRequestHandleResult::Io { input } => {
            arg = Some(TimerRequestHandleArg::Socket(socket_handle(&mut stream, input).unwrap()))
        }
        TimerRequestHandleResult::TimeIo { input } => {
            arg = Some(TimerRequestHandleArg::Time(time_handle(input).unwrap()))
        }
        TimerRequestHandleResult::Err { err } => panic!("{err}"),
    }
}

More examples

See projects built on top of this library:

Sponsoring

nlnet

Special thanks to the NLnet foundation and the European Commission that helped the project to receive financial support from various programs:

If you appreciate the project, feel free to donate using one of the following providers:

GitHub Ko-fi Buy Me a Coffee Liberapay thanks.dev PayPal

About

I/O-free time library written in Rust

Topics

Resources

License

Apache-2.0, MIT licenses found

Licenses found

Apache-2.0
LICENSE-APACHE
MIT
LICENSE-MIT

Contributing

Security policy

Stars

Watchers

Forks

Contributors