Can use node_modules/luvabase/manifest-schema.json for editor validation.
identifier
string
Yes
Globally unique URL-safe and lowercased identifier for the app, for example luvabase-snake. No dots or special characters other than hyphens. Must be 3-50 characters and start with a letter. The -proxy suffix is reserved by Luvabase so app identifiers cannot end with it.
name
string
Yes
Name of the app, for example Snake. Must be 3-30 characters.
subtitle
string
No
Subtitle of the app, for example Play the classic of classics. Must be 3-50 characters.
icon
string
No
Relative path of the app icon inside the .luva app file, for example images/icon.png.
screenshots
string[]
No
Relative paths of app screenshots, for example ["images/screenshot1.png", "images/screenshot2.png"].
description
string
No
Full description of the app. Maximum 10,000 characters.
surfaces
Surface[]
No
Places where this app can be used. Defaults to [ { "type": "web" } ] when omitted. Use [] for no launch surfaces.
accessLevel
"members" | "public"
No
Who can access the pod. Defaults to members if omitted. If public, no authorization is performed by the runtime, but you can still limit access as normal by returning not-allowed errors, etc.
proxyResponses
Record<string, string>
No
Public plain-text responses for exact app proxy paths. These responses bypass app proxy authentication and are intended for domain-verification challenges.
repository
string
No
URL of the source code repository if open source, for example https://github.com/luvabase/snake.
Use proxyResponses when a third party needs a fixed response from the app proxy domain before it can authenticate. Each key must be an absolute path without a query string or fragment. Only exact GET requests match; query strings are ignored when matching the path. Responses use status 200, Content-Type: text/plain; charset=utf-8, and Cache-Control: no-store.
These paths are public. The built-in /.well-known/oauth-protected-resource response is reserved by Luvabase and takes precedence over a manifest entry.