1
0
Fork 0
arangodb/Documentation/Books/Users/AqlExamples/Join.mdpp

168 lines
3.7 KiB
Plaintext

!CHAPTER Joins
So far we have only dealt with one collection (`users`) at a time. We also have a
collection `relations` that stores relationships between users. We will now use
this extra collection to create a result from two collections.
First of all, we'll query a few users together with their friends' ids. For that,
we'll use all `relations` that have a value of `friend` in their `type` attribute.
Relationships are established by using the `from` and `to` attributes in the
`relations` collection, which point to the `id` values in the `users` collection.
!SUBSECTION Join tuples
We'll start with a SQL-ish result set and return each tuple (user name, friend id)
separately. The AQL query to generate such result is:
FOR u IN users
FILTER u.active == true
LIMIT 0, 4
FOR f IN relations
FILTER f.type == "friend" && f.from == u.id
RETURN {
"user" : u.name,
"friendId" : f.to
}
[
{
"user" : "Abigail",
"friendId" : 108
},
{
"user" : "Abigail",
"friendId" : 102
},
{
"user" : "Abigail",
"friendId" : 106
},
{
"user" : "Fred",
"friendId" : 209
},
{
"user" : "Mary",
"friendId" : 207
},
{
"user" : "Mary",
"friendId" : 104
},
{
"user" : "Mariah",
"friendId" : 203
},
{
"user" : "Mariah",
"friendId" : 205
}
]
!SUBSECTION Horizontal lists
Note that in the above result, a user might be returned multiple times. This is the
SQL way of returning data. If this is not desired, the friends' ids of each user
can be returned in a horizontal list. This will return each user at most once.
The AQL query for doing so is:
FOR u IN users
FILTER u.active == true LIMIT 0, 4
RETURN {
"user" : u.name,
"friendIds" : (
FOR f IN relations
FILTER f.from == u.id && f.type == "friend"
RETURN f.to
)
}
[
{
"user" : "Abigail",
"friendIds" : [
108,
102,
106
]
},
{
"user" : "Fred",
"friendIds" : [
209
]
},
{
"user" : "Mary",
"friendIds" : [
207,
104
]
},
{
"user" : "Mariah",
"friendIds" : [
203,
205
]
}
]
In this query we are still iterating over the users in the `users` collection
and for each matching user we are executing a sub-query to create the matching
list of related users.
!SUBSECTION Self joins
To not only return friend ids but also the names of friends, we could "join" the
`users` collection once more (something like a "self join"):
FOR u IN users
FILTER u.active == true
LIMIT 0, 4
RETURN {
"user" : u.name,
"friendIds" : (
FOR f IN relations
FILTER f.from == u.id && f.type == "friend"
FOR u2 IN users
FILTER f.to == u2.id
RETURN u2.name
)
}
[
{
"user" : "Abigail",
"friendIds" : [
"Jim",
"Jacob",
"Daniel"
]
},
{
"user" : "Fred",
"friendIds" : [
"Mariah"
]
},
{
"user" : "Mary",
"friendIds" : [
"Isabella",
"Michael"
]
},
{
"user" : "Mariah",
"friendIds" : [
"Madison",
"Eva"
]
}
]