🗂️ resman
Runtime managed resource borrowing.
This library provides a map that can store one of any type, as well as mutable borrows to each type at the same time.
Note: This implementation is extracted from shred
, with the
following differences:
Debug
implementation prints out the type name instead of type ID for the key.- Uses
downcast-rs
instead ofmopa
for downcasting types. - Adds
Debug
andPartialEq
implementations for borrow types when the resource type implements those traits. - Returns
Err
instead of panicking fortry_borrow*
functions when the resource is already borrowed.
Usage
Add the following to Cargo.toml
= "0.16.0"
# or
= { = "0.17.0", = ["debug"] }
= { = "0.17.0", = ["fn_res"] }
= { = "0.17.0", = ["fn_res", "fn_res_mut"] }
= { = "0.17.0", = ["fn_res", "fn_meta"] }
= { = "0.17.0", = ["fn_res", "fn_res_mut", "fn_meta"] }
# requires nightly
= { = "0.17.0", = ["fn_res", "fn_res_mut", "fn_res_once"] }
In code:
use Resources;
;
;
let mut resources = default;
resources.insert;
resources.insert;
// We can validly have two mutable borrows from the `Resources` map!
let mut a = resources.;
let mut b = resources.;
a.0 = 2;
b.0 = 3;
// We need to explicitly drop the A and B borrows, because they are runtime
// managed borrows, and rustc doesn't know to drop them before the immutable
// borrows after this.
drop;
drop;
// Multiple immutable borrows to the same resource are valid.
let a_0 = resources.;
let _a_1 = resources.;
let b = resources.;
println!;
println!;
// Trying to mutably borrow a resource that is already borrowed (immutably
// or mutably) returns `Err`.
let a_try_borrow_mut = resources.;
let exists = if a_try_borrow_mut.is_ok else ;
println!; // prints "Err"
Features
"debug"
:
The Debug
implementation for Resources
will use the Debug
implementation for the values when printed. This requires that all
Resources
to also implement Debug
.
Example:
use Resources;
let mut resources = default;
resources.insert;
println!;
// Without `"debug"` feature:
// {u32: ".."}
// With `"debug"` feature:
// {u32: 1}
"fn_res"
:
Enables the FnRes
trait, allowing dynamic functions invocation under a
generic function type.
Usage of this API is as follows:
-
Define regular functions or closures to run.
- The functions should take
&T
or&mut T
as parameters. - The return type of all functions should be the same.
Currently there is a limit of 7 parameters.
- The functions should take
-
Call
my_function.into_fn_res()
to obtain aBox<dyn FnRes>
. -
Call
fn_res.call(&resources)
to automatically borrowT
fromresources
and invoke the function.
Example:
use ;
/// Borrows `u32` mutably, and `u64` immutably.
/// Borrows `u32` immutably, and `u64` mutably.
let functions = ;
let mut resources = default;
resources.insert;
resources.insert;
let sum = functions
.iter
.fold;
assert_eq!; // 1 + 2 + 2
let debug_str = format!;
assert!;
assert!;
Since Resources
has internal mutability, care must be taken to not run
multiple functions that borrow the same value mutably from Resources
at
the same time when using FnRes::call
, otherwise it will panic.
Use FnRes::try_call
for a non-panicking version, which will return a
BorrowFail
error if there is an overlapping borrow conflict at runtime.
"fn_res_mut"
:
Like "fn_res"
, enables the IntoFnResMut
and FnResMut
traits.
FnResMut
is implemented for functions and closures that impl FnMut
, but
not Fn
.
"fn_res_once"
:
Requires nightly
Like "fn_res_mut"
, enables the IntoFnResOnce
and FnResOnce
traits.
FnResOnce
is implemented for functions and closures that impl FnOnce
,
but not FnMut
.
"fn_meta"
:
Adds FnMeta
as an implied trait to FnRes
. This means function
metadata can be queried for any FnRes
.
"high_arg_count"
:
Raises the number of arguments that FnRes
, IntoFnRes
, and
IntoFnResource
are implemented for from 6 to 8.
This is feature gated because compilation time increasing significantly with
higher numbers of arguments -- as much as from 4 seconds for 6 arguments
to 26 seconds for 8 arguments when only "fn_res"
is enabled, and up to a
minute when "fn_mut"
and "fn_once"
are enabled.
See Also
anymap
: Map of any type, without multiple mutable borrows.rt_map
: Runtime managed mutable borrowing from a map.shred
: ContainsResources
type, plus a task dispatcher.
License
Licensed under either of
- Apache License, Version 2.0, (LICENSE-APACHE or https://www.apache.org/licenses/LICENSE-2.0)
- MIT license (LICENSE-MIT or https://opensource.org/licenses/MIT)
at your option.
Contribution
Unless you explicitly state otherwise, any contribution intentionally submitted for inclusion in the work by you, as defined in the Apache-2.0 license, shall be dual licensed as above, without any additional terms or conditions.