Skip to content

Commit

Permalink
Fix false assumption of vertex_type being singleton (#445)
Browse files Browse the repository at this point in the history
* Fix false assumption of vertex_type being singleton

* add test to ensure we fixed it
  • Loading branch information
u9g committed Aug 17, 2023
1 parent 42e7c5c commit 84a2b4a
Show file tree
Hide file tree
Showing 2 changed files with 67 additions and 11 deletions.
16 changes: 5 additions & 11 deletions trustfall_core/src/schema/adapter/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -426,19 +426,13 @@ impl<'a> crate::interpreter::Adapter<'a> for SchemaAdapter<'a> {
let schema = self.schema;
let destination = resolve_info.destination();

// The `Schema` vertex is a singleton -- there can only be one instance of it.
// So this hint can only be used once, and we don't want to clone it needlessly.
// Take it from this option and assert that it hasn't been taken more than once.
let mut vertex_type_name =
Some(destination.statically_required_property("name").map(|x| x.cloned()));
// `.cloned()` to get rid of reference, so we can own it when we need to move it later
let vertex_type_name =
destination.statically_required_property("name").map(|x| x.cloned());

resolve_neighbors_with(contexts, move |_| {
vertex_type_iter(
schema,
vertex_type_name.take().expect(
"found more than one Schema vertex when resolving vertex_type",
),
)
// `.clone()` each time as we may have multiple "vertex_type" edges
vertex_type_iter(schema, vertex_type_name.clone())
})
}
"entrypoint" => {
Expand Down
62 changes: 62 additions & 0 deletions trustfall_core/src/schema/adapter/tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -145,6 +145,68 @@ fn check_schema_then_vertex_type() {
);
}

#[test]
fn use_vertex_type_in_schema_edge_multiple_times() {
#[derive(Debug, PartialEq, Eq, serde::Deserialize, PartialOrd, Ord)]
struct Output {
name: String,
property: String,
other_vertices: u64,
}

let query = r#"
{
Schema {
vertex_type {
name @filter(op: "one_of", value: ["$name"]) @output @tag
property {
property: name @output
}
}
vertex_type @fold @transform(op: "count") @output(name: "other_vertices") {
name @filter(op: "!=", value: ["%name"])
}
}
}"#;
let args = btreemap! {
"name".into() => vec!["VertexType", "Property"].into(),
}
.into();
let adapter = Arc::new(SchemaAdapter::new(&SCHEMA));

let indexed = crate::frontend::parse(&SCHEMA, query).expect("not a valid query");
let mut rows = crate::interpreter::execution::interpret_ir(adapter, indexed, args)
.expect("execution error")
.map(|x| x.try_into_struct::<Output>().expect("invalid conversion"))
.collect::<Vec<_>>();
rows.sort_unstable();

assert_eq!(
rows,
vec![
Output { name: "Property".to_owned(), property: "docs".to_owned(), other_vertices: 4 },
Output { name: "Property".to_owned(), property: "name".to_owned(), other_vertices: 4 },
Output { name: "Property".to_owned(), property: "type".to_owned(), other_vertices: 4 },
Output {
name: "VertexType".to_owned(),
property: "docs".to_owned(),
other_vertices: 4
},
Output {
name: "VertexType".to_owned(),
property: "is_interface".to_owned(),
other_vertices: 4
},
Output {
name: "VertexType".to_owned(),
property: "name".to_owned(),
other_vertices: 4
}
]
);
}

#[test]
fn check_entrypoint_target_edges() {
let query = r#"
Expand Down

0 comments on commit 84a2b4a

Please sign in to comment.