Skip to main content
moon supports an integrated query language, known as MQL (moon query language), that can be used to filter and select projects and tasks from the project graph using an SQL-like syntax. MQL is primarily used by moon exec and moon run with the --query option.

Syntax

The query language uses a familiar SQL-inspired syntax that combines fields, comparison operators, and logical operators to build powerful filters.

Comparisons

A comparison (also known as an assignment) is an expression that defines a piece of criteria. This criteria maps a field to a value with an explicit comparison operator.

Equals, Not equals

The equals (=) and not equals (!=) comparison operators can be used for exact value matching.
projectLayer=library && language!=javascript
You can also define a list of values using square bracket syntax that will match against one of the values:
language=[javascript, typescript]

Like, Not like

The like (~) and not like (!~) comparison operators can be used for wildcard value matching using glob syntax.
projectSource~packages/* && tag!~*-app
Like comparisons can only be used on non-enum fields (strings). They cannot be used on fields like language, projectLayer, taskType, etc.

Conditions

The && and || logical operators can be used to combine multiple comparisons into a condition:
  • && - Logical AND (all conditions must match)
  • || - Logical OR (at least one condition must match)
taskToolchain=system || taskToolchain=node
For readability, you can also use AND or OR:
taskToolchain=system OR taskToolchain=node
Mixing both && and || operators in the same condition is not supported. Use parentheses to create sub-groups instead.

Grouping

For advanced queries and complex conditions, you can group comparisons using parentheses to create logical groupings. Groups can also be nested within other groups.
language=javascript && (taskType=test || taskType=build)
Nested groups:
(language=javascript || language=typescript) && (projectLayer=library || (projectStack=frontend && tag~react-*))

Fields

The following fields can be used as criteria in your queries. These fields are related to task tokens.

Project fields

language

Programming language the project is written in, as defined in moon.*.
language=rust
Supported values: bash, batch, javascript, typescript, rust, go, python, ruby, php, etc.

project

Name OR alias of the project.
project=server

projectAlias

Alias of the project. For example, the package.json name.
projectAlias~@scope/*

projectId

Name of the project, as defined in .moon/workspace.*, or id in moon.*.
projectId=server

projectLayer

The project layer, as defined in moon.*.
projectLayer=application
Supported values: application, infrastructure, library, tool, unknown

projectSource

Relative file path from the workspace root to the project root, as defined in .moon/workspace.*.
projectSource~packages/*

projectStack

The project stack, as defined in moon.*.
projectStack=frontend
Supported values: backend, frontend, systems, infrastructure, unknown

tag

A tag within the project, as defined in moon.*.
tag~react-*

Task fields

task

ID/name of a task within the project.
task=[build,test]

taskToolchain

The toolchain a task will run against, as defined in moon.*.
taskToolchain=node
Supported values: system, node, bun, deno, rust, go, python, etc.

taskType

The type of task, based on its configured settings.
taskType=build
Supported values: build, run, test

Examples

Filter by language

Run tests for all JavaScript projects:
moon exec :test --query "language=javascript"

Filter by project layer

Build all library projects:
moon exec :build --query "projectLayer=library"

Combine multiple conditions

Run tests for TypeScript projects in the frontend stack:
moon exec :test --query "language=typescript && projectStack=frontend"

Use OR conditions

Build projects using either Node or Bun toolchains:
moon exec :build --query "taskToolchain=node || taskToolchain=bun"

Complex grouped queries

Run tests for React or Vue projects, but only in libraries:
moon exec :test --query "projectLayer=library && (tag~react-* || tag~vue-*)"

Pattern matching with globs

Run builds for all packages in a specific directory:
moon exec :build --query "projectSource~packages/core/*"

Filter by task type

Run all build tasks across all projects:
moon exec :build --query "taskType=build"

Query validation

When building queries, moon validates:
  • Empty queries - Queries must contain at least one comparison
  • Unknown fields - All field names must be valid
  • Unknown values - Enum fields must use valid values
  • Operator mixing - Cannot mix && and || in the same condition without grouping
  • Like operators - Cannot use ~ or !~ on enum fields
  • Syntax errors - All queries must be syntactically valid
If validation fails, moon will display a clear error message indicating what went wrong.

Implementation details

The query language is implemented using:
  • Parser - Uses the Pest parsing library with a custom grammar
  • AST - Builds an abstract syntax tree from the parsed query
  • Criteria builder - Converts the AST into structured criteria
  • Query executor - Evaluates criteria against projects and tasks
Queries are cached per input string to improve performance on repeated executions.

Build docs developers (and LLMs) love