Lock Expressions
Lock expressions control access to commands, exits, and objects. They appear in
three places:
- The
lockfield of a command definition:lock: "connected & builder+" - The in-game
@lockcommand:@lock north=admin - The SDK
u.checkLock()method in scripts
An empty or absent lock always passes — the object or command is accessible to
everyone, including unauthenticated connections.
Flag Checks
The simplest lock is a single flag name. It passes if the actor has that flag
set on their object.
"connected" -- actor must be logged in
"player" -- actor must be a player
"builder" -- actor must have the builder flag
"admin" -- actor must have the admin flag
"wizard" -- actor must have the wizard flag
"superuser" -- actor must have the superuser flag
Level-based checks (flag+)
Append + to a flag name to mean that level or any higher level. Because
flags have numeric levels, builder+ passes for builders, storytellers, admins,
wizards, and superusers alike.
| Expression | Passes for |
|---|---|
player |
player only |
player+ |
player, builder, storyteller, admin, wizard, superuser |
builder |
builder only |
builder+ |
builder, storyteller, admin, wizard, superuser |
admin+ |
admin, wizard, superuser |
Note:
connectedhas no numeric level — use it without+.
Boolean Operators
Lock expressions support full boolean algebra. Operators evaluate with the
following precedence (highest first):
!— NOT (prefix)&— AND|— OR( )— Grouping (overrides precedence)
"!superuser" -- actor does NOT have superuser
"connected & admin+" -- connected AND admin or higher
"admin | wizard" -- admin OR wizard
"connected & (admin | builder)" -- connected AND (admin or builder)
"!player" -- actor is not a player (e.g. a guest or object)
Combining connected with a flag
A common pattern: require login and a minimum permission level.
"connected & admin+" -- most staff commands
"connected & builder+" -- building commands
"connected" -- any logged-in player
DB Reference Checks
Use #id to restrict access to a specific database object.
"#1" -- passes only if the actor IS object #1
"connected & #5" -- connected AND the actor is object #5
This is useful for owner-only exits or objects that only a specific character
should be able to use.
Attribute Checks
Check a value stored in an actor’s state (attributes). The syntax is
attribute:value.
"sex:Male" -- actor's 'sex' attribute equals "Male" (case-insensitive key)
"class:Warrior" -- actor's 'class' attribute equals "Warrior"
Numeric attributes support comparison operators:
"level:>5" -- actor's 'level' is greater than 5
"level:>=10" -- actor's 'level' is 10 or more
"gold:<100" -- actor's 'gold' is less than 100
"gold:<=50" -- actor's 'gold' is 50 or less
Attribute names are case-insensitive. Values are compared as strings unless a
comparison operator is present, in which case they’re parsed as numbers.
Indirect Locks
Prefix @ to delegate the lock check to the lock stored on another object.
This lets you centralise a lock definition and point many commands at it.
"@#10" -- evaluate the lock on object #10
"@vault" -- evaluate the lock on the object named "vault"
Indirect locks are recursion-protected (maximum depth 10) to prevent cycles.
Script Checks
Embed inline script code between [ and ]. The lock passes if the code
returns a truthy value.
"[u.me.state.karma > 50]"
"[await u.db.get(u.me.id) !== undefined]"
Script locks have access to the u SDK object in scope. Use sparingly — they
run synchronously inside the lock check and should be fast.
Using Locks in Scripts
The SDK exposes u.checkLock() to evaluate a lock expression from inside a
script:
// Check if an actor passes a lock
const canEnter = await u.checkLock(targetRoom, "connected & builder+");
if (!canEnter) {
u.send("You don't have permission to enter.");
return;
}
Signature:
u.checkLock(target: string | IDBObj, lock: string): Promise<boolean>
target— the object whose perspective is used to resolve@indirectlockslock— any valid lock expression string
Quick Reference
| Expression | Meaning |
|---|---|
"" |
Always passes (open) |
"connected" |
Actor is logged in |
"player" |
Actor has the player flag |
"builder+" |
Builder level or higher |
"admin+" |
Admin level or higher |
"superuser" |
Superuser only |
"!admin" |
Actor is NOT an admin |
"admin | wizard" |
Admin or wizard |
"connected & admin+" |
Logged in AND admin+ |
"connected & (admin | builder)" |
Logged in AND (admin or builder) |
"#5" |
Actor is object #5 |
"sex:Female" |
Actor’s sex attribute is “Female” |
"level:>=10" |
Actor’s level attribute is ≥ 10 |
"@#10" |
Delegates to the lock on object #10 |
"[u.me.state.vip]" |
Passes if actor’s vip state is truthy |