> ## Documentation Index
> Fetch the complete documentation index at: https://docs.bijection.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Class: Relation<Expr>

> A declarative relation.

[server](/api/modules/server).Relation

A declarative relation. Construct this with q.table, never with a database callback.

## Type parameters

| Name |
| :- |
| `Expr` |

## Constructors

### constructor

• **new Relation**\<`Expr`>(`expression`)

#### Type parameters

| Name |
| :- |
| `Expr` |

#### Parameters

| Name | Type |
| :- | :- |
| `expression` | [`RelationExpression`](/api/modules/server#relationexpression) |

## Properties

### expressionType

• `Readonly` **expressionType**: `Expr`

***

### expression

• `Readonly` **expression**: [`RelationExpression`](/api/modules/server#relationexpression)

## Methods

### as

▸ **as**\<`Name`>(`alias`): [`Relation`](/api/classes/server.Relation)\<[`Alias`](/api/modules/server#alias)\<`Expr`, `Name`>>

#### Type parameters

| Name | Type |
| :- | :- |
| `Name` | extends `string` |

#### Parameters

| Name | Type |
| :- | :- |
| `alias` | `Name` |

#### Returns

[`Relation`](/api/classes/server.Relation)\<[`Alias`](/api/modules/server#alias)\<`Expr`, `Name`>>

***

### filter

▸ **filter**\<`Predicate`>(`predicate`): [`Relation`](/api/classes/server.Relation)\<[`Filter`](/api/modules/server#filter)\<`Expr`, `Predicate`>>

#### Type parameters

| Name | Type |
| :- | :- |
| `Predicate` | extends [`Expression`](/api/classes/server.Expression)\<`boolean`, `Predicate`> |

#### Parameters

| Name | Type |
| :- | :- |
| `predicate` | `Predicate` |

#### Returns

[`Relation`](/api/classes/server.Relation)\<[`Filter`](/api/modules/server#filter)\<`Expr`, `Predicate`>>

***

### select

▸ **select**\<`Fields`>(`fields`): [`Relation`](/api/classes/server.Relation)\<[`Select`](/api/modules/server#select)\<`Expr`, `Fields`>>

#### Type parameters

| Name | Type |
| :- | :- |
| `Fields` | extends [`Selection`](/api/modules/server#selection) |

#### Parameters

| Name | Type |
| :- | :- |
| `fields` | `Fields` |

#### Returns

[`Relation`](/api/classes/server.Relation)\<[`Select`](/api/modules/server#select)\<`Expr`, `Fields`>>

***

### leftJoin

▸ **leftJoin**\<`Right`, `Options`>(`right`, `options`): [`Relation`](/api/classes/server.Relation)\<[`Join`](/api/modules/server#join)\<`Expr`, `Right`, `"left"`, `Options`>>

#### Type parameters

| Name | Type |
| :- | :- |
| `Right` | `Right` |
| `Options` | extends [`ViewJoinOptions`](/api/modules/server#viewjoinoptions) |

#### Parameters

| Name | Type |
| :- | :- |
| `right` | [`Relation`](/api/classes/server.Relation)\<`Right`> |
| `options` | `Options` |

#### Returns

[`Relation`](/api/classes/server.Relation)\<[`Join`](/api/modules/server#join)\<`Expr`, `Right`, `"left"`, `Options`>>

***

### innerJoin

▸ **innerJoin**\<`Right`, `Options`>(`right`, `options`): [`Relation`](/api/classes/server.Relation)\<[`Join`](/api/modules/server#join)\<`Expr`, `Right`, `"inner"`, `Options`>>

#### Type parameters

| Name | Type |
| :- | :- |
| `Right` | `Right` |
| `Options` | extends [`ViewJoinOptions`](/api/modules/server#viewjoinoptions) |

#### Parameters

| Name | Type |
| :- | :- |
| `right` | [`Relation`](/api/classes/server.Relation)\<`Right`> |
| `options` | `Options` |

#### Returns

[`Relation`](/api/classes/server.Relation)\<[`Join`](/api/modules/server#join)\<`Expr`, `Right`, `"inner"`, `Options`>>

***

### exists

▸ **exists**\<`Right`, `Options`>(`right`, `options`): [`Relation`](/api/classes/server.Relation)\<[`Join`](/api/modules/server#join)\<`Expr`, `Right`, `"semi"`, `Options`>>

Keep each row, once, when at least one row of `right` has equal keys
(an existence or semi join). Rows are never multiplied and the result
has this relation's fields only, so `right` needs no alias. Keys compare
as every join's do: null equals null, a missing value equals only a
missing value. Only relations over virtual tables accept it; views refuse it.

#### Type parameters

| Name | Type |
| :- | :- |
| `Right` | `Right` |
| `Options` | extends [`ViewExistsOptions`](/api/modules/server#viewexistsoptions) |

#### Parameters

| Name | Type |
| :- | :- |
| `right` | [`Relation`](/api/classes/server.Relation)\<`Right`> |
| `options` | `Options` |

#### Returns

[`Relation`](/api/classes/server.Relation)\<[`Join`](/api/modules/server#join)\<`Expr`, `Right`, `"semi"`, `Options`>>

***

### notExists

▸ **notExists**\<`Right`, `Options`>(`right`, `options`): [`Relation`](/api/classes/server.Relation)\<[`Join`](/api/modules/server#join)\<`Expr`, `Right`, `"anti"`, `Options`>>

Keep each row, once, when no row of `right` has equal keys (an anti
join). A row whose key is null is kept only when `right` has no null
key. Otherwise as [exists](/api/classes/server.Relation#exists).

#### Type parameters

| Name | Type |
| :- | :- |
| `Right` | `Right` |
| `Options` | extends [`ViewExistsOptions`](/api/modules/server#viewexistsoptions) |

#### Parameters

| Name | Type |
| :- | :- |
| `right` | [`Relation`](/api/classes/server.Relation)\<`Right`> |
| `options` | `Options` |

#### Returns

[`Relation`](/api/classes/server.Relation)\<[`Join`](/api/modules/server#join)\<`Expr`, `Right`, `"anti"`, `Options`>>

***

### aggregate

▸ **aggregate**\<`Name`, `From`, `Aggregates`>(`alias`, `options`): [`Relation`](/api/classes/server.Relation)\<[`Aggregate`](/api/modules/server#aggregate)\<`Expr`, `Name`, `From`, `Aggregates`>>

Add `alias` to each row: the measures of the rows of `from` related to
it. A row whose related rows are none gets zero counts and sums, and no
percentile; a denied or unavailable read refuses instead.

#### Type parameters

| Name | Type |
| :- | :- |
| `Name` | extends `string` |
| `From` | `From` |
| `Aggregates` | extends `Record`\<`string`, [`ViewAggregate`](/api/modules/server#viewaggregate)> |

#### Parameters

| Name | Type |
| :- | :- |
| `alias` | `Name` |
| `options` | `Object` |

#### Returns

[`Relation`](/api/classes/server.Relation)\<[`Aggregate`](/api/modules/server#aggregate)\<`Expr`, `Name`, `From`, `Aggregates`>>

***

### groupBy

▸ **groupBy**\<`Fields`>(`fields`, `window?`): `Object`

#### Type parameters

| Name | Type |
| :- | :- |
| `Fields` | extends readonly `string`\[] |

#### Parameters

| Name | Type |
| :- | :- |
| `fields` | `Fields` |
| `window?` | [`ViewWindow`](/api/modules/server#viewwindow) |

#### Returns

`Object`

| Name | Type |
| :- | :- |
| `aggregate` | \<Aggregates>(`aggregates`: `Aggregates`) => [`Relation`](/api/classes/server.Relation)\<[`Group`](/api/modules/server#group)\<`Expr`, `Fields`, `Aggregates`>> |

***

### orderBy

▸ **orderBy**(`keys`): [`Relation`](/api/classes/server.Relation)\<[`Sort`](/api/modules/server#sort)\<`Expr`>>

Rows in the order of `keys`, ties broken by the complete row ascending.
Ascending order places a missing field first, then null, then values;
text compares by UTF-8 bytes. Only relations over virtual tables accept a sort;
views refuse it.

#### Parameters

| Name | Type |
| :- | :- |
| `keys` | readonly (`string` \| [`ViewSortKey`](/api/modules/server#viewsortkey))\[] |

#### Returns

[`Relation`](/api/classes/server.Relation)\<[`Sort`](/api/modules/server#sort)\<`Expr`>>

***

### limit

▸ **limit**(`rows`): [`Relation`](/api/classes/server.Relation)\<[`Sort`](/api/modules/server#sort)\<`Expr`>>

The first `rows` rows (top-N). After `orderBy` they are the first rows
of that order; otherwise of the complete row ascending, so a limit never
picks arbitrary rows. A limit changes the answer. `maxRowSteps` bounds
the work needed to produce that answer, including intermediate rows.

#### Parameters

| Name | Type |
| :- | :- |
| `rows` | `number` |

#### Returns

[`Relation`](/api/classes/server.Relation)\<[`Sort`](/api/modules/server#sort)\<`Expr`>>


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.