> For the complete documentation index, see [llms.txt](https://sweet-tooth.gitbook.io/specmonstah/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://sweet-tooth.gitbook.io/specmonstah/tutorial/03-queries.md).

# 03: queries

Section 3's source file begins:

```scheme
(ns reifyhealth.specmonstah-tutorial.03
  (:require [reifyhealth.specmonstah.core :as sm]
            [loom.io :as lio]))

(def schema
  {:user {:prefix :u}
   :post {:prefix    :p
          :relations {:owner-id [:user :id]}}})

(defn ex-01
  []
  (sm/add-ents {:schema schema} {:post [[2]]}))
```

Queries are used to specify what ents should get generated. The term *query* might throw you off because usually it's used to refer to the language for *retrieving* records from a database. In Specmonstah, I think of queries as allowing you to express, *generate the minimal ent-db necessary for me to retrieve the ents I've specified*.

In `ex-01`, the query passed to `sm/add-ents` is `{:post [[2]]}`. This is like saying, *I want two `:post`s. Create an ent-db with the minimum ents needed so that I can retrieve them.* Because `:post` ents must refer to a `:user`, Specmonstah generates the `:user` ent `:u0`. Specmonstah only generates one `:user`, not two, because that's the minimum needed to satisfy the query.

Queries are maps, where each key is the name of an ent type, and each value is a vector of *query terms*. In the query `{:post [[2]]}`, `:post` is an ent type and `[2]` is a query term.

Each query term is a vector where the first element is either a number or an *ent name*. When you provide a number, as in `[2]`, you're instructing SM to generate that many ents of the given ent type, and to name them according to its default naming system. As we saw in the last section, SM names ents by appending an index to the ent type's `:prefix`. The `:prefix` for `:post` is `:p`, so the `:post` ents are named `:p0` and `:p1`. Figuring out what to name your test data is one of the tedious aspects of testing that SM handles for you.

On the other hand, if you *do* want to name an ent, you can provide a keyword as the first element in the query term, as in `ex-02`:

```scheme
(defn ex-02
  []
  (sm/add-ents {:schema schema} {:post [[:my-post]
                                        [:blorp-post]]}))

(sm/view (ex-02))
```

![](/files/-LowQnzxO_spj178UalA)

Here, you're naming your `:post` ents `:my-post` and, in a fit of near whimsy, `:blorp-post`.

You can add as many query terms to an ent type as you want, mixing numbers and ent names as you please:

```scheme
(defn ex-03
  []
  (sm/add-ents {:schema schema} {:post [[1]
                                        [:work]
                                        [1]
                                        [:cones-of-dunshire-club]]}))
```

![](/files/-LowQql5RY-RUFW6dh2G)

Query terms take a second argument, an options map map, which is used to further tune the creation of the ent. The next section will show you how to use the options map to generate unique references.


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://sweet-tooth.gitbook.io/specmonstah/tutorial/03-queries.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
