#!/usr/bin/env nu
# Invoke lian-build for this project, render-profile aware.
#
# The render profile (leptos-hydration | htmx-ssr) is derived, never declared:
# check-wasm-needed.nu reads site/config/rendering.ncl (same decision source as
# `just build-auto` and `just dev`) and decides whether a wasm32/cargo-leptos
# build is required. build_directives.ncl exports one directive per profile;
# this script extracts the matching field (via a tiny wrapper NCL) and feeds
# that single directive to lian-build, so the disjoint leptos/htmx builds —
# different base images, Dockerfile and artifacts — are selected automatically.
#
# Usage: nu provisioning/build.nu [--keep-runner] [--dry-run] [--profile <p>]
# Env: DEV_ROOT (default /Users/Akasha/Development), LIAN_BUILD_ROOT, SECRETS_BASE, SSH_KEY

def find-lian-build [lb_root: string]: nothing -> string {
    let on_path = (do { ^which lian-build } | complete)
    if $on_path.exit_code == 0 and (($on_path.stdout | str trim) | is-not-empty) {
        return ($on_path.stdout | str trim)
    }
    let release_bin = $"($lb_root)/target/release/lian-build"
    if ($release_bin | path exists) { return $release_bin }
    print "[build.nu] lian-build not found — running cargo build --release"
    do { cd $lb_root; ^cargo build --release -p lian-build } | complete
        | if $in.exit_code != 0 { error make { msg: "cargo build failed" } } else { ignore }
    $release_bin
}

# Decide the render profile. An explicit --profile wins; otherwise run the
# shared wasm detector against rendering.ncl. Falls back to parsing
# default_profile from rendering.ncl when the detector is unavailable.
def resolve-profile [project_root: string, dev_root: string, forced: string]: nothing -> string {
    if ($forced | is-not-empty) {
        if $forced not-in ["leptos-hydration" "htmx-ssr"] {
            error make { msg: $"invalid --profile '($forced)' (leptos-hydration | htmx-ssr)" }
        }
        return $forced
    }

    let detector = $"($dev_root)/rustelo/scripts/check-wasm-needed.nu"
    if ($detector | path exists) {
        let res = (do {
            cd $project_root
            ^nu $detector --routes-dir site/config --workspace-config site/config/rendering.ncl
        } | complete)
        match $res.exit_code {
            0 => { return "leptos-hydration" }
            1 => { return "htmx-ssr" }
            _ => { error make { msg: $"check-wasm-needed.nu failed (exit ($res.exit_code)): ($res.stderr | str trim)" } }
        }
    }

    # Fallback: read default_profile directly.
    let ncl = $"($project_root)/site/config/rendering.ncl"
    let p = (open $ncl | parse --regex 'default_profile = "(?P<p>[^"]+)"' | get p?.0? | default "leptos-hydration")
    if $p == "htmx-ssr" { "htmx-ssr" } else { "leptos-hydration" }
}

def main [
    --keep-runner
    --dry-run
    --profile: string = ""   # force leptos-hydration | htmx-ssr (default: auto-detect)
]: nothing -> nothing {
    let dev_root     = ($env.DEV_ROOT? | default "/Users/Akasha/Development")
    let lb_root      = ($env.LIAN_BUILD_ROOT? | default $"($dev_root)/lian-build")
    let secrets_base = ($env.SECRETS_BASE? | default $"($dev_root)/project-provisioning/workspaces/secrets-base")
    let ssh_key      = ($env.SSH_KEY? | default $"($env.HOME)/.ssh/orchestrator-buildkit-key")
    let project_root = ($env.FILE_PWD | path dirname)

    let profile    = (resolve-profile $project_root $dev_root $profile)
    let directives = $"($project_root)/lian-build/build_directives.ncl"

    # Wrapper selecting the profile's directive. lian-build evaluates this with
    # its own nickel import paths, so build_directives.ncl's imports
    # (jpl-project.ncl, defaults/) resolve exactly as for the full file. Profile
    # names contain '-', so they are quoted field access: ."leptos-hydration".
    let wrapper = (^mktemp -t selected-directives.XXXXXX.ncl | str trim)
    ('(import "' + $directives + '")."' + $profile + '"') | save -f $wrapper

    print $"[build.nu] render profile: ($profile)"

    # Dry-run is cheap and side-effect free: no context assembly, no lian-build
    # compile. It reports the resolved profile and the directive selection only.
    if $dry_run {
        print $"[dry-run] directive ← ($directives) field '($profile)'"
        print $"[dry-run] wrapper: ((open $wrapper))"
        ^rm -f $wrapper
        return
    }

    let ctx = (^mktemp -d | str trim)
    ^just --justfile $"($lb_root)/justfile" _ctx-leptos $project_root $ctx

    let bin = (find-lian-build $lb_root)

    let args = [
        "build"
        "--directives"   $wrapper
        "--context"      $ctx
        "--ssh-key"      $ssh_key
        "--language"     "rust"
        "--secrets-base" $secrets_base
        "--runner-image" "app=buildkit-runner-golden"
    ]
    let args = if $keep_runner { $args | append "--keep-runner" } else { $args }

    with-env { LIAN_BUILD_NICKEL_IMPORT_PATH: $lb_root } {
        run-external $bin ...$args
    }

    ^rm -rf $ctx $wrapper
}
