If you have a node’s uid and you’d like to create a new node with some predicate values copied over, can you do that in one transaction or do you have to query and then set a new node?
Hi @MiLeung
Unfortunately, there is no direct clone function supported yet. You could explore the upsert block.
In this example, I was able to “clone” a string and an int value. However the upsert has to be run twice (explained below).
Source Data:
{
set{
_:a <name> "andy" .
_:a <age> "30" .
}
}
Upsert Block
This needs to be run twice; once to create and link a clone node, and in the second run, clone the value themselves. In order to yield a single scalar value for respective attributes from the source, I had to use an aggregate function.
upsert{
query{
source as var(func:uid(<0xc>)){
clone as clonedTo
}
clonedFrom(func: uid(clone)){
~clonedTo{
a as age
n1 as name
}
x as max(val(a))
xn as max(val(n1))
}
}
mutation {
set{
uid(source) <clonedTo> uid(clone) .
uid(clone) <name> val(xn) .
uid(clone) <age> val(x) .
}
}
}
There is worked out solution here for edges in a data merging context here. Please review that as well.
IMO we should consider supportingfirstValue
as an aggregate function. That would help to solve such requirements without resorting to max
functions. It would be an elegant solution.
Thanks. I would also need functionality to clone a node’s uid value predicates, so I’ll just have to use a query then set mutation for now.