Zones API
The Zones API lets you create, manage, and query zones within The Grid. All endpoints are served from https://api.a-new-world.com/api/zones. Endpoints require authentication unless noted otherwise.
Zone Discovery
List Zones
GET /api/zones?page=1&limit=20&search=mall&size_tier=district&sort=visit_count
Returns a paginated list of public, active zones.
Query Parameters:
| Param | Type | Default | Description |
|---|---|---|---|
search | string | — | Search zones by name or description |
size_tier | string | — | Filter by plot, district, region, realm |
sort | string | visit_count | visit_count, created_at, name, rating_sum |
page | number | 1 | Page number |
limit | number | 20 | Results per page (max: 50) |
Response:
{
"zones": [...],
"pagination": { "page": 1, "limit": 20, "total": 342, "pages": 18 }
}
Featured Zones
GET /api/zones/featured
Returns developer-curated featured zones (up to 20). Rotates weekly.
Trending Zones
GET /api/zones/trending?period=week
Zones ranked by recent visitor count. period: day, week (default), month.
Nearby Zones
GET /api/zones/nearby?x=5&y=-3&radius=10
Returns zones within a coordinate radius (max radius: 100). Sorted by distance.
Zone CRUD
Get Zone
GET /api/zones/:id
Returns full zone details including settings and metadata. No auth required.
Create Zone ✅ Auth
POST /api/zones
Purchase and create a new zone. Credits are deducted atomically.
Request Body:
{
"name": "Crystal Mall",
"description": "A sprawling shopping center",
"size_tier": "district",
"coord_x": 5,
"coord_y": -3,
"visibility": "public",
"theme": "shopping"
}
Tier Pricing:
| Tier | Dimensions | Cost |
|---|---|---|
plot | 64×64×64 | 100 credits |
district | 256×256×128 | 500 credits |
region | 1024×1024×256 | 2,500 credits |
realm | 4096×4096×512 | 10,000 credits |
Validation:
name— 2–64 characterssize_tier— required, one of the abovecoord_x,coord_y— must not overlap existing zones- Player must have sufficient credits
Errors: 400 (validation), 402 (insufficient credits), 409 (coordinates occupied)
Update Zone ✅ Auth (Owner Only)
PATCH /api/zones/:id
Update zone metadata. Supports partial updates.
Fields: name, description, visibility, theme, max_players, settings
Archive Zone ✅ Auth (Owner Only)
DELETE /api/zones/:id
Soft-deletes the zone (sets status to archived). The Nexus cannot be deleted.
Zone Connection
Join Zone ✅ Auth
GET /api/zones/:id/join
Validates access and returns dedicated server connection info. This is the entry point for connecting to a zone's multiplayer session.
Access checks (single consolidated query):
- Zone exists and is active
- Player is not banned
- Player has access (public = open, private/invite-only = membership or ownership required)
Response (dedicated server available):
{
"zone_id": "zone_abc123",
"server_host": "192.168.1.100",
"server_port": 7777,
"visit_token": "eyJ...",
"player_count": 12,
"max_players": 50
}
The client uses server_host:server_port to travel to the UE5 dedicated server, passing the visit_token as a URL parameter.
Response (no server available):
{ "error": "No active server for this zone" }
Errors: 404 (inactive/missing), 403 (banned/denied), 503 (no server available)
Zone Blocks
Get Blocks (Chunked)
GET /api/zones/:id/blocks?chunk_x=0&chunk_y=0&chunk_z=0
Returns all blocks within a 32×32×32 chunk. Used for proximity-based block streaming.
Response:
{
"chunk": { "x": 0, "y": 0, "z": 0 },
"blocks": [
{
"id": "block_abc",
"x": 5, "y": 10, "z": 0,
"block_type": "cube",
"asset_id": "asset_tex001",
"rotation": 0,
"scale_x": 1, "scale_y": 1, "scale_z": 1,
"placed_by": "user_xyz",
"metadata": null
}
]
}
Note: Real-time block operations (place/remove) are handled via UE5 dedicated server RPCs. The REST endpoint is for initial loading and streaming.
Zone Members & Roles ✅ Auth
List Roles
GET /api/zones/:zoneId/roles
Create Role (Admin+)
POST /api/zones/:zoneId/roles
{
"name": "Shop Staff",
"color": "#e67e22",
"permissions": ["subzone.build", "subzone.assets", "chat.moderate"],
"priority": 5
}
Delete Role (Admin+)
DELETE /api/zones/:zoneId/roles/:roleId
Removes the role and all member assignments with that role.
List Members
GET /api/zones/:zoneId/members
Returns members with their usernames, avatars, and assigned role names.
Assign Role
POST /api/zones/:zoneId/members
{ "user_id": "user_abc", "role_id": "role_builder" }
Assigns a role to a member in this zone.
Remove Member
DELETE /api/zones/:zoneId/members/:userId
Zone Bans ✅ Auth (Admin+)
List Bans
GET /api/zones/:zoneId/bans
Ban Player
POST /api/zones/:zoneId/bans
{
"user_id": "user_xyz",
"reason": "Griefing",
"duration_hours": 24
}
Omit duration_hours for a permanent ban. Zone owners cannot be banned.
Unban Player
DELETE /api/zones/:zoneId/bans/:userId
Sub-Zones ✅ Auth
List Sub-Zones
GET /api/zones/:zoneId/sub-zones
Create Sub-Zone (Owner Only)
POST /api/zones/:zoneId/sub-zones
{
"name": "Store A1",
"bounds_min": [10, 0, 10],
"bounds_max": [30, 16, 30],
"rent_price": 100,
"rent_cycle": "monthly",
"max_blocks": 5000
}
Validation:
- Bounds must be within zone dimensions
- No overlap with existing sub-zones (AABB test)
- Sub-zone count must be within tier limit (Plot: 2, District: 8, Region: 32, Realm: 256)
Lease Sub-Zone
POST /api/zones/:zoneId/sub-zones/:subId/lease
Rents a sub-zone. Credits are deducted immediately for the first billing cycle. 95% goes to the zone owner, 5% platform commission. Rent renews automatically via daily cron — see rent collection.
Delete Sub-Zone (Owner Only)
DELETE /api/zones/:zoneId/sub-zones/:subId
Portals ✅ Auth
List Portals
GET /api/zones/:zoneId/portals
Create Portal (Owner or zone.portals permission)
POST /api/zones/:zoneId/portals
{
"target_zone_id": "zone_xyz",
"source_x": 10, "source_y": 0, "source_z": 5,
"target_x": 0, "target_y": 0, "target_z": 5,
"name": "To Market Square",
"bidirectional": true
}
If bidirectional is true, a reverse portal is automatically created in the target zone.
Delete Portal
DELETE /api/zones/:zoneId/portals/:portalId
Credits
Get Balance ✅ Auth
GET /api/credits
{
"balance": 4350,
"lifetime_earned": 12000,
"lifetime_spent": 7650
}
Transaction History ✅ Auth
GET /api/credits/transactions?page=1&limit=50
Purchase Credits ✅ Auth
POST /api/credits/purchase
{ "pack": "creator" }
Returns a Stripe Checkout Session URL.
Error Codes
All errors follow the format { "error": "message" } with the appropriate HTTP status code.
| Code | Meaning |
|---|---|
400 | Validation error (bad input) |
401 | Missing or invalid JWT |
402 | Insufficient credits |
403 | Access denied (not owner, banned, insufficient permissions) |
404 | Resource not found or inactive |
409 | Conflict (coordinates occupied, already connected, sub-zone overlap) |
503 | Zone is full (player capacity reached) |