# Rustelo Manifest Contracts
#
# Type validation for rustelo.manifest.ncl files.
# Generated by `cargo rustelo new` from template + framework options.
# Evaluated at runtime by ManifestResolver (rustelo_utils::manifest).
#
# JSON output is deserialized into rustelo_utils::manifest::RusteloManifest.

{
  ManifestMeta = {
    version
      | String
      | doc "Manifest schema version",

    schema
      | String
      | doc "Schema URL for IDE/tooling support"
      | optional,
  },

  ProjectInfo = {
    name
      | String
      | doc "Implementation name (matches Cargo workspace package name)",

    type
      | String
      | doc "Project type: 'rustelo-app' | 'rustelo-plugin'",

    description
      | String
      | doc "Human-readable description"
      | optional,
  },

  PathConfig = {
    content
      | String
      | doc "Content root, relative to manifest location",

    config
      | String
      | doc "NCL configuration root (site/config/index.ncl entrypoint)",

    routes
      | String
      | doc "Routes configuration directory",

    i18n
      | String
      | doc "FTL locales root directory",

    assets
      | String
      | doc "Public static assets directory served as-is",

    ui
      | String
      | doc "UI configuration root (menus, themes, footer — now in NCL)",

    build_output
      | String
      | doc "Leptos site output directory",

    wasm_output
      | String
      | doc "WASM package output directory",
  },

  # PAP: language and content-type discovery is always config-driven.
  # Use 'auto' to discover from site/config/index.ncl [site.languages]
  # and [content_types]. Explicit lists are allowed for restricted deploys.
  DiscoveryConfig = {
    default_lang
      | String
      | doc "Default language ISO 639-1 code (e.g. 'en')",

    languages
      | String
      | doc "'auto' = discovered from site config | explicit = 'en,es,fr'",

    content_types
      | String
      | doc "'auto' = discovered from site config | explicit = 'blog,recipes'",
  },

  # Deployment values that vary between environments.
  # Resolved from environment variables at evaluation time via std.env.try_var.
  # Credentials and secrets belong ONLY in environment variables, never here.
  DeploymentConfig = {
    base_url
      | String
      | doc "Site base URL — set BASE_URL env var to override",

    content_url
      | String
      | doc "URL prefix for content serving (e.g. '/r')",

    content_root
      | String
      | doc "Content URL path segment (matches content_url without leading slash)",

    cache_path
      | String
      | doc "Runtime cache directory name",

    api_endpoint
      | String
      | doc "API base path — set API_ENDPOINT env var to override",

    database_url
      | String
      | doc "Database connection URL — set DATABASE_URL env var to override",
  },

  BuildConfig = {
    leptos_output_name
      | String
      | doc "Leptos output name (must match [[workspace.metadata.leptos]].name in Cargo.toml)",

    site_addr
      | String
      | doc "Development server listen address",

    reload_port
      | Number
      | doc "Hot-reload WebSocket port",

    debug
      | Number
      | doc "Debug verbosity: 0=off 1=basic 2=verbose 3=trace routes 4=deep trace"
      | default = 0,

    cache_build_path
      | String
      | doc "Build cache subdirectory name (placed under target/)",
  },

  # Cargo feature flags for this implementation.
  # These control compile-time code inclusion — distinct from runtime feature flags.
  # The generator (cargo rustelo new) sets these from --features arguments.
  FrameworkFeatures = {
    auth
      | Bool
      | doc "JWT/OAuth2/2FA authentication"
      | default = true,

    content
      | Bool
      | doc "Markdown/static content management"
      | default = true,

    email
      | Bool
      | doc "SMTP email support"
      | default = false,

    tls
      | Bool
      | doc "HTTPS/TLS via rustls"
      | default = false,

    metrics
      | Bool
      | doc "Prometheus metrics endpoint"
      | default = false,

    crypto
      | Bool
      | doc "AES-GCM encryption for sensitive config values"
      | default = false,

    # Allow implementation-specific feature flags without breaking the contract
    ..
  },

  RusteloManifest = {
    manifest
      | ManifestMeta,

    project
      | ProjectInfo,

    paths
      | PathConfig,

    discovery
      | DiscoveryConfig,

    deployment
      | DeploymentConfig,

    build
      | BuildConfig,

    features
      | FrameworkFeatures
      | doc "Cargo feature flags enabled for this implementation"
      | optional,
  },
}
