jobq: a job asks for the ids it wants back
The operator's instruction on the issue was "the closure returns an array of guids, and enqueue_job returns the node ids in that order". What was here instead returned a HashMap of everything inserted, and no caller used the keys: submit dropped the return, insert_group did into_values(), and the scheduler ignored what append_subgraph handed back. The guid-keyed lookup was dead weight, and into_values() made that Vec arbitrarily ordered -- harmless only because nothing read it. insert_job now takes FnOnce(&JobBuilder) -> Vec<NodeGuid> and returns the matching ids positionally. A handle from another job is UnknownNode rather than a silent omission: the return is positional, so a short vector would misalign every id after it. c0re's Declare stays FnOnce(&Job) and the wrapper names no handles in one place, rather than ending seven templates in an empty vector -- a DAG is addressed by its container node, which submit inserts itself. That frees insert_group from needing every id, so the node_rt pre-seeding goes too: NodeRuntime is one Option field and every reader already tolerated a missing entry (entry().or_default(), get().and_then(), iter().find()). The tests are the argument for the shape: capturing a handle through a mutable binding to look it up in the map afterwards collapses into returning it and destructuring the result.
This commit is contained in:
parent
c82853af5a
commit
bf138ae79a
7 changed files with 147 additions and 76 deletions
|
|
@ -458,26 +458,33 @@ impl<N, R> Graph<N, R> {
|
|||
Ok(id)
|
||||
}
|
||||
|
||||
/// Insert a whole job under `root_parent`, returning the id each handle's
|
||||
/// node was minted as.
|
||||
/// Insert a whole job under `root_parent`, returning the ids of the nodes
|
||||
/// `declare` **asked for**, in the order it named them.
|
||||
///
|
||||
/// `declare` receives a fresh [`JobBuilder`] and names the job's nodes on
|
||||
/// it; the builder never leaves this call, so a job cannot be built in one
|
||||
/// place and inserted in another. The graph-only counterpart of
|
||||
/// `declare` receives a fresh [`JobBuilder`], names the job's nodes on it,
|
||||
/// and returns the handles whose ids it wants back. The builder never
|
||||
/// leaves this call, so a job cannot be built in one place and inserted in
|
||||
/// another. The graph-only counterpart of
|
||||
/// [`crate::scheduler::Scheduler::insert_job`] — prefer that one when a
|
||||
/// scheduler owns the graph, since it also records what it started.
|
||||
///
|
||||
/// Asking is how a caller addresses a node it created: the alternative — a
|
||||
/// map of everything inserted, or a positional vector — either hands back a
|
||||
/// lookup nobody performs or reintroduces the counting this API exists to
|
||||
/// remove.
|
||||
///
|
||||
/// # Errors
|
||||
/// Propagates [`BuildError`] — a forward reference in the job's own
|
||||
/// declarations, a handle from a different job, or a graph rejection.
|
||||
pub fn insert_job(
|
||||
&mut self,
|
||||
root_parent: Option<NodeId>,
|
||||
declare: impl FnOnce(&JobBuilder<N, R>),
|
||||
) -> Result<std::collections::HashMap<NodeGuid, NodeId>, BuildError> {
|
||||
declare: impl FnOnce(&JobBuilder<N, R>) -> Vec<NodeGuid>,
|
||||
) -> Result<Vec<NodeId>, BuildError> {
|
||||
let job = JobBuilder::new();
|
||||
declare(&job);
|
||||
job.insert_into(self, root_parent)
|
||||
let wanted = declare(&job);
|
||||
let ids = job.insert_into(self, root_parent)?;
|
||||
crate::builder::resolve_wanted(&wanted, &ids)
|
||||
}
|
||||
|
||||
/// Borrow a node by id.
|
||||
|
|
|
|||
Loading…
Reference in a new issue