diff --git a/Cargo.lock b/Cargo.lock index d5cd11a..53d7c73 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -120,6 +120,15 @@ version = "0.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7a81dae078cea95a014a339291cec439d2f232ebe854a9d672b796c6afafa9b7" +[[package]] +name = "fastrand" +version = "1.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a7a407cfaa3385c4ae6b23e84623d48c2798d06e3e6a1878f7f59f17b3f86499" +dependencies = [ + "instant", +] + [[package]] name = "getrandom" version = "0.2.8" @@ -146,6 +155,15 @@ dependencies = [ "libc", ] +[[package]] +name = "instant" +version = "0.1.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7a5bbe824c507c5da5956355e86a746d82e0e1464f65d862cc5e71da70e94b2c" +dependencies = [ + "cfg-if", +] + [[package]] name = "libc" version = "0.2.137" @@ -233,6 +251,24 @@ dependencies = [ "proc-macro2", ] +[[package]] +name = "redox_syscall" +version = "0.2.16" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fb5a58c1855b4b6819d59012155603f0b22ad30cad752600aadfcb695265519a" +dependencies = [ + "bitflags", +] + +[[package]] +name = "remove_dir_all" +version = "0.5.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3acd125665422973a33ac9d3dd2df85edad0f4ae9b00dafb1a05e43a9f5ef8e7" +dependencies = [ + "winapi", +] + [[package]] name = "strsim" version = "0.10.0" @@ -258,6 +294,21 @@ dependencies = [ "chumsky", "clap", "pretty", + "tempfile", +] + +[[package]] +name = "tempfile" +version = "3.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5cdb1ef4eaeeaddc8fbd371e5017057064af0911902ef36b39801f67cc6d79e4" +dependencies = [ + "cfg-if", + "fastrand", + "libc", + "redox_syscall", + "remove_dir_all", + "winapi", ] [[package]] diff --git a/Cargo.toml b/Cargo.toml index 3a7b52e..2e725f7 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -8,3 +8,4 @@ anyhow = "1.0.66" chumsky = "0.8.0" clap = { version = "4.0.26", features = ["derive", "deprecated"] } pretty = "0.11.3" +tempfile = "3.3.0" diff --git a/src/main.rs b/src/main.rs index 0192a59..a40fedc 100644 --- a/src/main.rs +++ b/src/main.rs @@ -14,8 +14,9 @@ // Clippy lints #![warn(clippy::use_self)] -use std::fs; +use std::io::Write; use std::path::PathBuf; +use std::{fs, process}; use anyhow::anyhow; use chumsky::Parser as _; @@ -32,9 +33,19 @@ mod value; #[derive(Parser)] enum Command { - Parse { file: PathBuf }, - Pretty { file: PathBuf }, - Desugar { file: PathBuf }, + Parse { + file: PathBuf, + }, + Pretty { + file: PathBuf, + }, + Desugar { + file: PathBuf, + #[arg(long, short, default_value = "diff")] + difftool: String, + #[arg(long, short = 'a')] + diffarg: Vec, + }, } #[derive(Parser)] @@ -72,14 +83,23 @@ fn main() -> anyhow::Result<()> { println!("{}", pretty::pretty_to_string(program, 100)); } - Command::Desugar { file } => { + Command::Desugar { + file, + difftool, + diffarg, + } => { let content = fs::read_to_string(&file)?; let stream = span::stream_from_str(&content); let mut program = parser::parser() .parse(stream) .map_err(|e| anyhow!("{e:?}"))?; - println!("{}", pretty::pretty_to_string(program.clone(), 100)); + let mut builder = tempfile::Builder::new(); + builder.suffix(".tada"); + + let mut prev = builder.tempfile()?; + prev.write_all(pretty::pretty_to_string(program.clone(), 100).as_bytes())?; + prev.flush()?; loop { let (new_program, desugared) = program.desugar(); @@ -88,10 +108,18 @@ fn main() -> anyhow::Result<()> { break; } - println!(); - println!("================================================================================"); - println!(); - println!("{}", pretty::pretty_to_string(program.clone(), 100)); + let mut cur = builder.tempfile()?; + cur.write_all(pretty::pretty_to_string(program.clone(), 100).as_bytes())?; + cur.flush()?; + + process::Command::new(&difftool) + .args(&diffarg) + .arg(prev.path()) + .arg(cur.path()) + .spawn()? + .wait()?; + + prev = cur; } } }