use serde::{Deserialize, Serialize};
use crate::runtime::store::{DispatchError, DispatchOutcome, NodeGraphStore};
use crate::schema::{NodeInstantiation, NodeInstantiationError, NodeRegistry};
use jellyflow_core::core::{CanvasPoint, NodeId, NodeKindKey, PortId};
pub const CREATE_NODE_TRANSACTION_LABEL: &str = "create node";
#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
pub struct CreateNodeRequest {
pub kind: NodeKindKey,
pub pos: CanvasPoint,
}
impl CreateNodeRequest {
pub fn new(kind: NodeKindKey, pos: CanvasPoint) -> Self {
Self { kind, pos }
}
}
#[derive(Debug, Clone)]
pub struct CreateNodeOutcome {
pub instantiation: NodeInstantiation,
pub dispatch: DispatchOutcome,
}
impl CreateNodeOutcome {
pub fn node_id(&self) -> NodeId {
self.instantiation.node_id
}
pub fn port_ids(&self) -> impl Iterator<Item = PortId> + '_ {
self.instantiation.ports.iter().map(|(id, _)| *id)
}
}
#[derive(Debug, thiserror::Error)]
pub enum CreateNodeError {
#[error(transparent)]
Schema(#[from] NodeInstantiationError),
#[error(transparent)]
Dispatch(#[from] DispatchError),
}
impl NodeGraphStore {
pub fn plan_create_node_from_schema(
&self,
registry: &NodeRegistry,
request: CreateNodeRequest,
) -> Result<NodeInstantiation, NodeInstantiationError> {
registry.instantiate_node(&request.kind, request.pos)
}
pub fn apply_create_node_from_schema(
&mut self,
registry: &NodeRegistry,
request: CreateNodeRequest,
) -> Result<CreateNodeOutcome, CreateNodeError> {
let instantiation = self.plan_create_node_from_schema(registry, request)?;
let tx = instantiation
.clone()
.into_labeled_transaction(CREATE_NODE_TRANSACTION_LABEL);
let dispatch = self.dispatch_transaction(&tx)?;
Ok(CreateNodeOutcome {
instantiation,
dispatch,
})
}
}