Assertion that run conditions are `Send` does not work in most cases
- Dominant language
- Rust
- Stars
- 48.2k
- Forks
- 4.8k
- Avg merge
- 3d 16h
- Merged PRs (30d)
- 171
Description
## Bevy version
main
## What you did
I ran this:
```rs
use bevy::prelude::*;
use bevy::system::NonSendMarker;
fn noop() {}
fn non_send_condition(_: NonSendMarker) -> bool { true }
#[test]
#[should_panic]
fn should_panic() {
let mut world = World::new();
let mut schedule = Schedule::default();
schedule.add_systems(noop.run_if(non_send_condition));
schedule.initialize(&mut world).unwrap();
schedule.run(&mut world);
}
```
## What went wrong
The test did not succeed, no panic occurred.
## Additional information
While skimming the code I noticed [this function](https://dev-docs.bevy.org/src/bevy_ecs/schedule/config.rs.html#15-24):
```rs
fn new_condition(condition: impl SystemCondition) -> BoxedCondition {
let condition_system = IntoSystem::into_system(condition);
assert!(
condition_system.is_send(),
"SystemCondition `{}` accesses `NonSend` resources. This is not currently supported.",
condition_system.name()
);
Box::new(condition_system)
}
```
This cannot work in most cases, where the system is a `FunctionSystem`, because `System::is_send` is usually returned from `SystemMeta.flags`. These flags are [initially empty](https://dev-docs.bevy.org/src/bevy_ecs/system/function_system.rs.html#53), only after `System::initialize` for example `NonSend` [will update the flag](https://dev-docs.bevy.org/src/bevy_ecs/system/system_param.rs.html#1439). But no initialization happens here yet.
Personally I think it is a footgun that system methods like these do not return `Option`s or at least panic when they are not initialized.
Contributor guide
Research direction
Start with the reproduction in the issue and inspect bevy_ecs/schedule/config.rs, then follow the referenced System::is_send and initialization code in bevy_ecs/system/function_system.rs and bevy_ecs/system/system_param.rs. Run the example test and trace when the condition system's flags are populated. Done means the documented assertion behavior is correctly exercised for a non-Send run condition.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- rust
- Domain
- game-dev
- Issue type
- Bug
- Difficulty
- 3/5
- Estimated time
- 1-2 days
- Activity status
- Stale
- Clarity
- Mostly clear
- Newbie friendliness
- 55/100