feat(cli): compile

This commit is contained in:
2026-02-17 12:10:11 +08:00
parent 3cc7c7be75
commit ae5febd5dd
5 changed files with 35 additions and 12 deletions

2
.gitignore vendored
View File

@@ -7,3 +7,5 @@ flamegraph*.svg
perf.data*
profile.json.gz
prof.json
*.cpuprofile
*.cpuprofile.gz

View File

@@ -35,7 +35,7 @@ import { ATTR_POSITIONS, IS_PATH, mkAttrs, mkAttrsWithPos, mkFunction, type NixV
export type NixRuntime = typeof Nix;
const replBindings: Map<string, NixValue> = new Map;
const replBindings: Map<string, NixValue> = new Map();
export const Nix = {
createThunk,

View File

@@ -207,7 +207,6 @@ pub(crate) trait CodegenContext {
fn get_current_dir(&self) -> &Path;
fn get_store_dir(&self) -> &str;
fn get_current_source_id(&self) -> usize;
fn get_current_source(&self) -> crate::error::Source;
}
impl<Ctx: CodegenContext> Compile<Ctx> for ExprId {
@@ -500,16 +499,10 @@ impl<Ctx: CodegenContext> Compile<Ctx> for [(ExprId, ExprId)] {
for &(slot, inner) in self {
let inner_ir = ctx.get_ir(inner);
let inner_span = inner_ir.span();
code!(
buf, ctx;
"let expr" slot.0 "=Nix.createThunk(()=>(" inner_ir "),"
"\"expr" slot.0 " "
ctx.get_current_source().get_name() ":"
usize::from(inner_span.start()) ":"
usize::from(inner_span.end())
"\");"
"\"expr" slot.0 "\");"
);
}
}

View File

@@ -363,9 +363,6 @@ impl CodegenContext for Ctx {
.checked_sub(1)
.expect("current_source not set")
}
fn get_current_source(&self) -> crate::error::Source {
self.sources.last().expect("current_source not set").clone()
}
fn get_store_dir(&self) -> &str {
self.store.get_store_dir()
}

View File

@@ -26,6 +26,12 @@ struct Cli {
#[derive(Subcommand)]
enum Command {
Compile {
#[clap(flatten)]
source: ExprSource,
#[arg(long)]
silent: bool
},
Eval {
#[clap(flatten)]
source: ExprSource,
@@ -63,6 +69,30 @@ fn create_context(#[cfg(feature = "inspector")] cli: &Cli) -> Result<Context> {
Ok(Context::new()?)
}
fn run_compile(context: &mut Context, src: ExprSource, silent: bool) -> Result<()> {
let src = if let Some(expr) = src.expr {
Source::new_eval(expr)?
} else if let Some(file) = src.file {
Source::new_file(file)?
} else {
unreachable!()
};
match context.compile(src) {
Ok(compiled) => {
if !silent {
println!("{compiled}");
}
}
Err(err) => {
eprintln!("{:?}", miette::Report::new(*err));
exit(1);
}
};
#[cfg(feature = "inspector")]
context.wait_for_inspector_disconnect();
Ok(())
}
fn run_eval(context: &mut Context, src: ExprSource) -> Result<()> {
let src = if let Some(expr) = src.expr {
Source::new_eval(expr)?
@@ -150,6 +180,7 @@ fn main() -> Result<()> {
)?;
match cli.command {
Command::Compile { source , silent } => run_compile(&mut context, source, silent),
Command::Eval { source } => run_eval(&mut context, source),
Command::Repl => run_repl(&mut context),
}