#![allow(clippy::panic, clippy::print_stdout, clippy::print_stderr)] use std::{
env, fs,
path::{Path, PathBuf},
process::Command,
};
fn main() {
let manifest_dir = env::var("CARGO_MANIFEST_DIR").expect("CARGO_MANIFEST_DIR not set");
let studio_dir = Path::new(&manifest_dir).join("studio");
let dist_dir = studio_dir.join("dist");
println!("cargo:rerun-if-changed=studio/src/app.ts");
println!("cargo:rerun-if-changed=studio/package.json");
println!("cargo:rerun-if-changed=studio/tsconfig.json");
let node_modules = studio_dir.join("node_modules");
if !node_modules.exists() {
let status = Command::new("npm")
.args(["install", "--prefer-offline"])
.current_dir(&studio_dir)
.status();
match status {
Ok(s) if s.success() => {},
Ok(s) => panic!("npm install failed with status {s}"),
Err(e) => {
eprintln!("cargo:warning=npm not found ({e}), skipping Studio SPA build");
emit_fallback_dist(&dist_dir);
println!("cargo:rustc-env=FRAISEQL_STUDIO_DIST={}", dist_dir.display());
return;
},
}
}
let status = Command::new("npm").args(["run", "build"]).current_dir(&studio_dir).status();
match status {
Ok(s) if s.success() => {},
Ok(s) => panic!("npm run build failed with status {s}"),
Err(e) => {
eprintln!("cargo:warning=npm not found ({e}), skipping Studio SPA build");
emit_fallback_dist(&dist_dir);
},
}
println!("cargo:rustc-env=FRAISEQL_STUDIO_DIST={}", dist_dir.display());
}
fn emit_fallback_dist(dist_dir: &PathBuf) {
fs::create_dir_all(dist_dir).expect("failed to create studio/dist/");
let js_path = dist_dir.join("app.js");
if !js_path.exists() {
fs::write(&js_path, b"// FraiseQL Studio placeholder\n")
.expect("failed to write fallback app.js");
}
let css_path = dist_dir.join("app.css");
if !css_path.exists() {
fs::write(&css_path, b"/* FraiseQL Studio placeholder */\n")
.expect("failed to write fallback app.css");
}
}