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

# Rules reference

> Complete reference for security rules expressions

This is the full reference for everything you can use inside Lark security rule expressions. If you're new to rules, start with the [security rules overview](/platform/security-rules) first.

## Variables

These variables are available in every rule expression.

| Variable          | Type           | Description                                                                                                                                                     |
| ----------------- | -------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `auth`            | object \| null | The authenticated user. `null` if the client is unauthenticated.                                                                                                |
| `auth.uid`        | string         | The unique ID of the authenticated user.                                                                                                                        |
| `auth.provider`   | string         | The authentication provider (e.g., `"google"`, `"anonymous"`, `"password"`, `"facebook"`, `"github"`, `"twitter"`).                                             |
| `auth.token`      | object         | The contents of the auth token, including any custom claims.                                                                                                    |
| `data`            | snapshot       | A snapshot of the **current** data at this path, before the write.                                                                                              |
| `newData`         | snapshot       | A snapshot of the data that **would exist** after the write. The merged result of new data and existing data. Only available in `.write` and `.validate` rules. |
| `root`            | snapshot       | A snapshot of the root of the entire database. Use this to read data at other paths.                                                                            |
| `now`             | number         | The current server timestamp in milliseconds since epoch.                                                                                                       |
| `$wildcards`      | string         | Path segment captures. For example, a rule at `/users/$userId` makes `$userId` available as a string variable containing the matched key.                       |
| `lark.projectId`  | string         | The ID of the current project.                                                                                                                                  |
| `lark.databaseId` | string         | The ID of the current database (the database name, not including the project prefix).                                                                           |

<Note>
  `data` and `newData` are scoped to the current path where the rule is defined. Use `root` when you need to look up data elsewhere in your database.
</Note>

## Snapshot methods

The `data`, `newData`, and `root` variables are all snapshots. You can call these methods on any snapshot.

| Method              | Returns                  | Description                                                                                                                                                                                     |
| ------------------- | ------------------------ | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `val()`             | any                      | Returns the primitive value (string, number, boolean, null) at this snapshot. For snapshots with children, use `child()` to access nested values.                                               |
| `exists()`          | boolean                  | Returns `true` if this snapshot contains any data. Equivalent to `val() != null`.                                                                                                               |
| `hasChild(path)`    | boolean                  | Returns `true` if the specified child path exists. `path` can be a single key or a slash-separated path.                                                                                        |
| `hasChildren(keys)` | boolean                  | Returns `true` if **all** of the specified child keys exist. `keys` is an array of strings. With no arguments, returns `true` if the snapshot has any children.                                 |
| `parent()`          | snapshot                 | Returns a snapshot of the parent node. Fails if called on the root.                                                                                                                             |
| `child(path)`       | snapshot                 | Returns a snapshot of the child at the given path. `path` can be a single key or a deeper slash-separated path (e.g., `'address/city'`). If the child doesn't exist, returns an empty snapshot. |
| `getPriority()`     | string \| number \| null | Returns the priority of the data at this snapshot.                                                                                                                                              |
| `isString()`        | boolean                  | Returns `true` if the value is a string.                                                                                                                                                        |
| `isNumber()`        | boolean                  | Returns `true` if the value is a number.                                                                                                                                                        |
| `isBoolean()`       | boolean                  | Returns `true` if the value is a boolean.                                                                                                                                                       |

### Examples

```
// Check if the current data exists
data.exists()

// Check if the incoming data has both 'name' and 'score' children
newData.hasChildren(['name', 'score'])

// Read a sibling value
data.parent().child('status').val() === 'active'

// Look up data at another path entirely
root.child('admins/' + auth.uid).exists()

// Check a deeply nested child
data.child('stats/hp').val() > 0

// Type-check incoming data
newData.child('name').isString() && newData.child('score').isNumber()
```

## String methods

These methods are available on any string value in a rule expression, including `auth.uid`, `$wildcard` captures, and string values returned by `val()`.

| Method / Property                 | Returns | Description                                                                                   |
| --------------------------------- | ------- | --------------------------------------------------------------------------------------------- |
| `length`                          | number  | The length of the string. This is a property, not a method (no parentheses).                  |
| `contains(substring)`             | boolean | Returns `true` if the string contains the given substring.                                    |
| `beginsWith(substring)`           | boolean | Returns `true` if the string starts with the given prefix.                                    |
| `endsWith(substring)`             | boolean | Returns `true` if the string ends with the given suffix.                                      |
| `replace(substring, replacement)` | string  | Returns a copy of the string with **all** instances of `substring` replaced by `replacement`. |
| `toLowerCase()`                   | string  | Returns the string converted to lower case.                                                   |
| `toUpperCase()`                   | string  | Returns the string converted to upper case.                                                   |
| `matches(regex)`                  | boolean | Returns `true` if the string matches the given regular expression.                            |

### Examples

```
// Validate that a username is at least 3 characters
newData.child('username').val().length >= 3

// Check that an email looks valid
newData.child('email').val().matches(/^[^@]+@[^@]+\.[^@]+$/)

// Check a string prefix
auth.token.identifier.beginsWith('internal-')

// Escape periods for use as keys
newData.child('email').val().replace('.', '%2E')

// Case-insensitive lookup
root.child('users').child(auth.token.identifier.toLowerCase()).exists()
```

## Operators

Standard operators work inside rule expressions.

### Comparison

| Operator | Description                      |
| -------- | -------------------------------- |
| `===`    | Strict equality (type and value) |
| `!==`    | Strict inequality                |
| `<`      | Less than                        |
| `>`      | Greater than                     |
| `<=`     | Less than or equal to            |
| `>=`     | Greater than or equal to         |

<Note>
  `==` is treated as `===` and `!=` is treated as `!==` in rules. Both are strict comparisons; there is no loose equality.
</Note>

### Logical

| Operator | Description |
| -------- | ----------- |
| `&&`     | Logical AND |
| `\|\|`   | Logical OR  |
| `!`      | Logical NOT |

### Arithmetic

| Operator | Description                          |
| -------- | ------------------------------------ |
| `+`      | Addition (also string concatenation) |
| `-`      | Subtraction / negation               |
| `*`      | Multiplication                       |
| `/`      | Division                             |
| `%`      | Modulo                               |

### Ternary

| Operator | Description                                                      |
| -------- | ---------------------------------------------------------------- |
| `? :`    | Conditional expression. `condition ? valueIfTrue : valueIfFalse` |

<Tip>
  Use the `+` operator to build dynamic paths for `child()` lookups: `root.child('users/' + auth.uid + '/role').val() === 'admin'`.
</Tip>

## Query-based rules

You can restrict what queries clients are allowed to run by referencing `query.` expressions in your rules. This lets you enforce that clients include certain filters or limits.

### Query variables

| Expression              | Type                                | Description                                                          |
| ----------------------- | ----------------------------------- | -------------------------------------------------------------------- |
| `query.orderByKey`      | boolean                             | `true` if the query is ordered by key.                               |
| `query.orderByPriority` | boolean                             | `true` if the query is ordered by priority.                          |
| `query.orderByValue`    | boolean                             | `true` if the query is ordered by value.                             |
| `query.orderByChild`    | string \| null                      | The child key being ordered by, or `null` if not ordered by a child. |
| `query.startAt`         | string \| number \| boolean \| null | The start bound of the query, or `null` if none.                     |
| `query.endAt`           | string \| number \| boolean \| null | The end bound of the query, or `null` if none.                       |
| `query.equalTo`         | string \| number \| boolean \| null | The equality filter of the query, or `null` if none.                 |
| `query.limitToFirst`    | number \| null                      | The limit-to-first value, or `null` if none.                         |
| `query.limitToLast`     | number \| null                      | The limit-to-last value, or `null` if none.                          |

### Examples

Restrict access to a collection so clients can only read their own items:

```json theme={null}
{
  "rules": {
    "baskets": {
      ".read": "auth.uid !== null &&
                query.orderByChild === 'owner' &&
                query.equalTo === auth.uid"
    }
  }
}
```

A query that includes the required parameters succeeds:

```typescript theme={null}
db.ref('baskets')
  .orderByChild('owner')
  .equalTo(auth.currentUser.uid)
  .on('value', callback); // Succeeds
```

A query without the parameters fails:

```typescript theme={null}
db.ref('baskets')
  .on('value', callback); // PERMISSION_DENIED
```

Limit how much data a client can download:

```json theme={null}
{
  "rules": {
    "messages": {
      ".read": "query.orderByKey && query.limitToFirst <= 1000"
    }
  }
}
```

## What's next

<CardGroup cols={2}>
  <Card title="Rules examples" icon="code" href="/platform/rules-examples">
    See these building blocks in action with real-world patterns.
  </Card>

  <Card title="Security rules" icon="shield-halved" href="/platform/security-rules">
    Go back to the overview to understand how rules are structured and evaluated.
  </Card>
</CardGroup>
