Skip to content

Commit 02e7035

Browse files
OJ423gitbook-bot
authored andcommitted
GITBOOK-122: Added WOQL Query How-to Guides
1 parent 0afaa63 commit 02e7035

File tree

12 files changed

+409
-10
lines changed

12 files changed

+409
-10
lines changed
Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
---
2+
description: How to add a document using WOQL
3+
---
4+
5+
# Add a Document
6+
7+
{% hint style="info" %}
8+
To use this How-To, first [clone the Star Wars demo](../cloning-a-demo-project.md) into your team on TerminusCMS. You will then have full access to the data needed for this tutorial
9+
{% endhint %}
10+
11+
You can add a document in WOQL using the `insert_document` keyword.
12+
13+
```javascript
14+
let v = Vars("id");
15+
insert_document(doc({'@type' : 'Planet', label: 'Planet-X'}), v.id)
16+
```
17+
18+
We can also add documents by using a variable. For instance, we can create a new planet for each individual in the star wars universe as follows:
19+
20+
```javascript
21+
let v = Vars("person", "name");
22+
and(isa(v.person, "People"),
23+
triple(v.person,"label",v.name),
24+
insert_document(doc({'@type' : 'Planet', label: v.name})))
25+
```
Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
---
2+
description: How to delete a document using WOQL
3+
---
4+
5+
# Delete a Document
6+
7+
{% hint style="info" %}
8+
To use this How-To, first [clone the Star Wars demo](../cloning-a-demo-project.md) into your team on TerminusCMS. You will then have full access to the data needed for this tutorial
9+
{% endhint %}
10+
11+
It is possible to delete a document in WOQL using the `delete_document` keyword.
12+
13+
First lets insert a document.
14+
15+
```javascript
16+
let v = Vars("id");
17+
insert_document(doc({'@type' : 'Planet', label: 'Planet-X'}), v.id)
18+
```
19+
20+
Supposing we get back the following:
21+
22+
```json
23+
"Planet/01dd97a75800f01f43ab7ab55b6dd08f198dd34d2bdbbeeb7bf4edee45111863"
24+
```
25+
26+
Now we can delete it with:
27+
28+
```javascript
29+
delete_document("Planet/01dd97a75800f01f43ab7ab55b6dd08f198dd34d2bdbbeeb7bf4edee45111863")
30+
```
Lines changed: 111 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,111 @@
1+
---
2+
description: How to write filters in WOQL
3+
---
4+
5+
# Filter Documents
6+
7+
{% hint style="info" %}
8+
To use this How-To, first [clone the Star Wars demo](../cloning-a-demo-project.md) into your team on TerminusCMS. You will then have full access to the data needed for this tutorial
9+
{% endhint %}
10+
11+
Since WOQL is a datalog, filters are just part of the query. You can express negative information, or constraints on the variables in order to get a restriction down to the things you want.
12+
13+
For instance, we can write the following query in the query panel for the Star Wars demo:
14+
15+
```javascript
16+
let v = Vars("person","person_name","vehicle","vehicle_name");
17+
limit(10)
18+
.select(v.person_name, v.vehicle_name)
19+
.and(triple(v.vehicle, "pilot", v.person),
20+
triple(v.vehicle, "label", v.vehicle_name),
21+
triple(v.person, "label", v.person_name))
22+
```
23+
24+
This results in:
25+
26+
```json
27+
[ {"person_name": {"@type":"xsd:string", "@value":"Chewbacca"},
28+
"vehicle_name": {"@type":"xsd:string", "@value":"Millennium Falcon"}},
29+
{"person_name": {"@type":"xsd:string", "@value":"Han Solo"},
30+
"vehicle_name": {"@type":"xsd:string", "@value":"Millennium Falcon"}},
31+
{"person_name": {"@type":"xsd:string", "@value":"Lando Calrissian"},
32+
"vehicle_name": {"@type":"xsd:string", "@value":"Millennium Falcon"}},
33+
{"person_name": {"@type":"xsd:string", "@value":"Nien Nunb"},
34+
"vehicle_name": {"@type":"xsd:string", "@value":"Millennium Falcon"}},
35+
{"person_name": {"@type":"xsd:string", "@value":"Luke Skywalker"},
36+
"vehicle_name": {"@type":"xsd:string", "@value":"X-wing"}},
37+
{"person_name": {"@type":"xsd:string", "@value":"Wedge Antilles"},
38+
"vehicle_name": {"@type":"xsd:string", "@value":"X-wing"}},
39+
{"person_name": {"@type":"xsd:string", "@value":"Jek Tono Porkins"},
40+
"vehicle_name": {"@type":"xsd:string", "@value":"X-wing"}},
41+
{"person_name": {"@type":"xsd:string", "@value":"Biggs Darklighter"},
42+
"vehicle_name": {"@type":"xsd:string", "@value":"X-wing"}},
43+
{"person_name": {"@type":"xsd:string", "@value":"Darth Vader"},
44+
"vehicle_name": {"@type":"xsd:string", "@value":"TIE Advanced x1"}},
45+
{"person_name": {"@type":"xsd:string", "@value":"Boba Fett"},
46+
"vehicle_name": {"@type":"xsd:string", "@value":"Slave 1"}}
47+
]
48+
```
49+
50+
We can ask for a _specific_ example of a vehicle name by filtering on equality.
51+
52+
For instance:
53+
54+
```javascript
55+
let v = Vars("person","person_name","vehicle","vehicle_name");
56+
select(v.person_name, v.vehicle_name)
57+
.and(triple(v.vehicle, "pilot", v.person),
58+
triple(v.vehicle, "label", v.vehicle_name),
59+
triple(v.person, "label", v.person_name),
60+
eq(v.vehicle_name, string("Millennium Falcon")))
61+
```
62+
63+
Which results in:
64+
65+
```json
66+
[ {"person_name": {"@type":"xsd:string", "@value":"Chewbacca"},
67+
"vehicle_name": {"@type":"xsd:string", "@value":"Millennium Falcon"}},
68+
{"person_name": {"@type":"xsd:string", "@value":"Han Solo"},
69+
"vehicle_name": {"@type":"xsd:string", "@value":"Millennium Falcon"}},
70+
{"person_name": {"@type":"xsd:string", "@value":"Lando Calrissian"},
71+
"vehicle_name": {"@type":"xsd:string", "@value":"Millennium Falcon"}},
72+
{"person_name": {"@type":"xsd:string", "@value":"Nien Nunb"},
73+
"vehicle_name": {"@type":"xsd:string", "@value":"Millennium Falcon"}}
74+
]
75+
```
76+
77+
We can also write:
78+
79+
```javascript
80+
let v = Vars("person","person_name","vehicle","vehicle_name");
81+
select(v.person_name, v.vehicle_name)
82+
.and(triple(v.vehicle, "pilot", v.person),
83+
triple(v.vehicle, "label", v.vehicle_name),
84+
triple(v.person, "label", v.person_name),
85+
not(eq(v.vehicle_name, string("Millennium Falcon"))))
86+
```
87+
88+
In which we get the complement of the above.
89+
90+
Or, we can use the regex operator to get a wider variety, for instance:
91+
92+
```javascript
93+
let v = Vars("person","person_name","vehicle","vehicle_name","pattern");
94+
select(v.person_name, v.vehicle_name)
95+
.and(triple(v.vehicle, "pilot", v.person),
96+
triple(v.vehicle, "label", v.vehicle_name),
97+
triple(v.person, "label", v.person_name),
98+
regex("W.*", v.vehicle_name, [v.pattern]))
99+
```
100+
101+
In this case, we get:
102+
103+
```json
104+
[ {"person_name": {"@type":"xsd:string", "@value":"Darth Vader"},
105+
"vehicle_name": {"@type":"xsd:string", "@value":"TIE Advanced x1"}},
106+
{"person_name": {"@type":"xsd:string", "@value":"Arvel Crynyd"},
107+
"vehicle_name": {"@type":"xsd:string", "@value":"A-wing"}},
108+
{"person_name": {"@type":"xsd:string", "@value":"Chewbacca"},
109+
"vehicle_name": {"@type":"xsd:string", "@value":"AT-ST"}}
110+
]
111+
```

guides/how-to-guides/query-using-woql/group-results-in-woql.md

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -4,15 +4,15 @@ description: >-
44
and TerminusCMS
55
---
66

7-
# Group results in WOQL
7+
# Group Results in WOQL
88

99
{% hint style="info" %}
1010
To use this How-To, first [clone the Star Wars demo](../cloning-a-demo-project.md) into your team on TerminusCMS. You will then have full access to the data needed for this tutorial
1111
{% endhint %}
1212

13-
### How to use `GroupBy`
13+
### How to use `group_by`
1414

15-
If we need to group variables according to some criteria, we can create an aggregate of solutions using `groupBy`.
15+
If we need to group variables according to some criteria, we can create an aggregate of solutions using `group_by`.
1616

1717
A group by is composed of a _focus_, a _template_, and a _group_ together with a query.
1818

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
---
2+
description: A how-to guide showing mathematical operations in WOQL
3+
---
4+
5+
# Mathematical Operations
6+
7+
WOQL has a number of mathematical operations that can be performed. These include, `plus`, `minus`, `divide`, `times`, `div` (for integer division), `exp` and `floor`.
8+
9+
To use these operations you need to `evaluate` an arithmetic expression, and then you will be able to bind the result to a variable.
10+
11+
For instance:
12+
13+
```javascript
14+
let v = Vars("result");
15+
evaluate(times(2,3), v.result)
16+
```
17+
18+
This will store the value of 2 times 3 in the variable `result`. The bindings which result from this query are:
19+
20+
```json
21+
[ {"result": {"@type":"xsd:decimal", "@value":12}} ]
22+
```
23+
24+
You can also chain these together, to build up more complicated computations, or use the results obtained by queries to derive new values.
25+
26+
```javascript
27+
let v = Vars("result1", "result2");
28+
and(evaluate(times(2,3), v.result1),
29+
evaluate(times(v.result1,3), v.result2))
30+
```
31+
32+
Which results in:
33+
34+
```json
35+
[ {"result1": {"@type":"xsd:decimal", "@value":6},
36+
"result2": {"@type":"xsd:decimal", "@value":18}} ]
37+
```
Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,61 @@
1+
---
2+
description: A how-to guide to help you order query results using WOQL
3+
---
4+
5+
# Order Query Results
6+
7+
{% hint style="info" %}
8+
To use this How-To, first [clone the Star Wars demo](../cloning-a-demo-project.md) into your team on TerminusCMS. You will then have full access to the data needed for this tutorial
9+
{% endhint %}
10+
11+
### Ordering results using `order_by`
12+
13+
The `order_by` keyword will allow you to sort results.
14+
15+
```javascript
16+
let v = Vars("person", "label", "eyes", "group");
17+
limit(2)
18+
.order_by(["eyes", "desc"])
19+
.select(v.eyes, v.group)
20+
.group_by(
21+
"eyes",
22+
["label"],
23+
v.group,
24+
and(triple(v.person, "rdf:type", "@schema:People"),
25+
triple(v.person, "label", v.label),
26+
triple(v.person, "eye_color", v.eyes)))
27+
```
28+
29+
This returns the first two results of people, who have a given eye color, sorted by eye color, in reverse order.
30+
31+
To get the alternative order, you can write:
32+
33+
```javascript
34+
let v = Vars("person", "label", "eyes", "group");
35+
limit(2)
36+
.order_by(["eyes", "asc"])
37+
.select(v.eyes, v.group)
38+
.group_by(
39+
"eyes",
40+
["label"],
41+
v.group,
42+
and(triple(v.person, "rdf:type", "@schema:People"),
43+
triple(v.person, "label", v.label),
44+
triple(v.person, "eye_color", v.eyes)))
45+
```
46+
47+
Or simply:
48+
49+
```javascript
50+
let v = Vars("person", "label", "eyes", "group");
51+
limit(2)
52+
.order_by("eyes")
53+
.select(v.eyes, v.group)
54+
.group_by(
55+
"eyes",
56+
["label"],
57+
v.group,
58+
and(triple(v.person, "rdf:type", "@schema:People"),
59+
triple(v.person, "label", v.label),
60+
triple(v.person, "eye_color", v.eyes)))
61+
```
Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
---
2+
description: How to perform path queries using WOQL
3+
---
4+
5+
# Path Queries
6+
7+
{% hint style="info" %}
8+
To use this How-To, first [clone the Star Wars demo](../cloning-a-demo-project.md) into your team on TerminusCMS. You will then have full access to the data needed for this tutorial
9+
{% endhint %}
10+
11+
### How to use `path`
12+
13+
TerminusCMS gives us [path queries](../../reference-guides/path-queries.md) that allow us to express chains of relationships succinctly.
14+
15+
The `path` keyword enables you to find a path through the graph traversing intermediate edges. An example would be finding a group of individuals who have at some point shared a vehicle as pilots, or piloted another vehicle that was shared with someone. This is a _transitive_ relationship and will explore the entire graph.
16+
17+
For instance
18+
19+
```javascript
20+
let v = Vars("person1", "person2");
21+
path(v.person1, "(<pilot,pilot>)+", v.person2)
22+
```
23+
24+
This `path` means we follow the `pilot` field _backward_ (because of the `<` arrow), to the vehicle of which the person is a pilot and then follow it forwards `pilot>` any number of times _but at least once_ which is what the `+` means.
25+
26+
The path itself can also be returned by adding another field, as so:
27+
28+
```javascript
29+
let v = Vars("person1", "person2", "path");
30+
path(v.person1, "(<pilot,pilot>)+", v.person2, v.path)
31+
```
32+
33+
This can be inspected to understand the manner in which we got from `person1` to `person2`.
Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,68 @@
1+
---
2+
description: A how-to guide for querying arrays and Sets with WOQL
3+
---
4+
5+
# Query Arrays and Sets
6+
7+
{% hint style="info" %}
8+
To use this How-To, first [clone the Star Wars demo](../cloning-a-demo-project.md) into your team on TerminusCMS. You will then have full access to the data needed for this tutorial
9+
{% endhint %}
10+
11+
In TerminusDB there are a number of collection types, including `List`, `Set`, and `Array`.
12+
13+
While these all generate JSON lists through the document interface, they have different semantics due to their different realisation in the graph.
14+
15+
### Sets
16+
17+
Sets are the simplest objects in TerminusDB. They are simply edges with the same name that lead to more than one object.
18+
19+
For instance, an example the document:
20+
21+
```json
22+
{ "@type" : "Class",
23+
"@id" : "Person",
24+
"name" : "xsd:string",
25+
"friends" : { "@type" : "Set", "@class" : "Person" }
26+
}
27+
```
28+
29+
To search for results of friends in WOQL, we can simply use `triple`.
30+
31+
```javascript
32+
let v = Vars("id", "friend")
33+
triple(v.id, "friends", v.friend)
34+
```
35+
36+
If you want to get back the values in a specific order, you can use an `order_by` clause.
37+
38+
### Lists
39+
40+
To search a list of objects, you need to traverse the intermediate _cons cells_. The list is actually a graph structure shaped like:
41+
42+
```
43+
∘ → ∘ rest→ ∘ rest→ ∘ rest→ rdf:nil
44+
↓ first ↓ first ↓ first
45+
v0 v1 v2
46+
```
47+
48+
This can be traversed using a [path query](https://github.com/terminusdb/terminuscms-docs/blob/f799ffc8844244121380f929b269a6952804a974/reference-guides/path-queries.md) as follows:
49+
50+
```javascript
51+
let v = Vars("queue", "person")
52+
path(v.queue, "contacts,rdf:rest*,rdf:first", v.person)
53+
```
54+
55+
### Arrays
56+
57+
To search an array, you can use select, and group by.
58+
59+
```javascript
60+
let v = Vars("queue", "arr", "person", "index")
61+
order_by(v.index)
62+
.select(v.queue, v.person, v.index)
63+
.and(triple(v.queue, "contacts", v.arr),
64+
triple(v.arr, "sys:index", v.index),
65+
triple(v.arr, "sys:value", v.person))
66+
```
67+
68+
This will give you back the array value (a person) as well as the index in the array, in order.

0 commit comments

Comments
 (0)