Sorry for the delay, I missed the email notification containing the update.
After thinking about this more, I don’t think I can support doing this at the query level at all anymore (honestly after rereading my original proposed solution, I literally face palmed). Throughout our discussion I’ve never been able to shake the thought that doing this in the query feels like a hack. I think the best long term solution is essentially what I provided at the end of my last response. To reiterate:
The schema would be extended so that uid’s can also be defined as a list (which is currently the only behavior is supports), however just like the other standard datatypes, it can also be defined as being a single item. Then all mutations would be able to reject mutations which would violate this relationship.
I come from an SQL world, so here’s the solutions in SQL terms.
Assume we have 3 tables, schools, students, and schools_students (join table). Schools have many students, students each have 1 school. Obviously you could do this in SQL without the join table, but because all associations in Dgraph currently have the possibility of being many to many, this is the closest representation.
schools:
id (int)
name (string)
students:
id (int)
name (string)
schools_students:
school_id (int)
student_id (int)
Yours:
SELECT ...
FROM students
JOIN schools_students ON schools_students.student_id = students.id
JOIN schools ON schools..id = schools_students.school_id
GROUP BY students.id
Mine:
(At table creation)
ALTER TABLE `schools_students` ADD UNIQUE INDEX `student_id` (`student_id`);
SELECT ...
FROM students
JOIN schools_students ON schools_students.student_id = students.id
JOIN schools ON schools..id = schools_students.school_id
The difference:
The primary difference is that in my example, the schema is enforcing this association. It is impossible to end up breaking the 1 to 1 association assuming the database is doing it’s job. In your solution, the data can be out of spec allowing for the 1 to 1 association to become a 1 to many. In your proposed solution (@singleObject or @unary), your essentially doing what the group by is in this SQL example. This actually hides issues with the data. This also means that rather than throwing an error because something is violating this relationship, the database will happily continue on thinking that nothing is wrong.
Conclusion
While I think that your solution would technically solve the problem, I think it would end up causing more problems in the long term than it would solve. If Dgraph needs to be able to support one to one associations, then it needs to fully support one to one associations. This would means alterations at the schema level, and adhering to those restrictions during all mutations. Violating this relationship should result in an error just like saving a geo datatype in a datetime predicate would.
(Edit)
TLDR; don’t do this in the query, do it in the schema.
I’ve also posted the proposed change in dgraph’s github. I’m hoping maybe one of the dgraph developers can give us their 2 cents on the issue as well.
https://github.com/dgraph-io/dgraph/issues/2511