Add randomized tests for incremental diff
This commit is contained in:
parent
3a511db5c9
commit
a9871a7a70
5 changed files with 81 additions and 12 deletions
4
Cargo.lock
generated
4
Cargo.lock
generated
|
@ -102,15 +102,19 @@ dependencies = [
|
||||||
"anyhow",
|
"anyhow",
|
||||||
"chrono",
|
"chrono",
|
||||||
"collections",
|
"collections",
|
||||||
|
"ctor",
|
||||||
"editor",
|
"editor",
|
||||||
|
"env_logger 0.9.3",
|
||||||
"fs",
|
"fs",
|
||||||
"futures 0.3.28",
|
"futures 0.3.28",
|
||||||
"gpui",
|
"gpui",
|
||||||
"indoc",
|
"indoc",
|
||||||
"isahc",
|
"isahc",
|
||||||
"language",
|
"language",
|
||||||
|
"log",
|
||||||
"menu",
|
"menu",
|
||||||
"project",
|
"project",
|
||||||
|
"rand 0.8.5",
|
||||||
"regex",
|
"regex",
|
||||||
"schemars",
|
"schemars",
|
||||||
"search",
|
"search",
|
||||||
|
|
|
@ -37,3 +37,8 @@ tiktoken-rs = "0.4"
|
||||||
[dev-dependencies]
|
[dev-dependencies]
|
||||||
editor = { path = "../editor", features = ["test-support"] }
|
editor = { path = "../editor", features = ["test-support"] }
|
||||||
project = { path = "../project", features = ["test-support"] }
|
project = { path = "../project", features = ["test-support"] }
|
||||||
|
|
||||||
|
ctor.workspace = true
|
||||||
|
env_logger.workspace = true
|
||||||
|
log.workspace = true
|
||||||
|
rand.workspace = true
|
||||||
|
|
|
@ -283,3 +283,11 @@ pub async fn stream_completion(
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[cfg(test)]
|
||||||
|
#[ctor::ctor]
|
||||||
|
fn init_logger() {
|
||||||
|
if std::env::var("RUST_LOG").is_ok() {
|
||||||
|
env_logger::init();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -204,14 +204,67 @@ impl Diff {
|
||||||
|
|
||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
mod tests {
|
mod tests {
|
||||||
use super::*;
|
use std::env;
|
||||||
|
|
||||||
#[test]
|
use super::*;
|
||||||
fn test_diff() {
|
use rand::prelude::*;
|
||||||
let mut diff = Diff::new("hello world".to_string());
|
|
||||||
dbg!(diff.push_new("hello"));
|
#[gpui::test(iterations = 100)]
|
||||||
dbg!(diff.push_new(" ciaone"));
|
fn test_random_diffs(mut rng: StdRng) {
|
||||||
// dbg!(diff.push_new(" world"));
|
let old_text_len = env::var("OLD_TEXT_LEN")
|
||||||
dbg!(diff.finish());
|
.map(|i| i.parse().expect("invalid `OLD_TEXT_LEN` variable"))
|
||||||
|
.unwrap_or(10);
|
||||||
|
let new_text_len = env::var("NEW_TEXT_LEN")
|
||||||
|
.map(|i| i.parse().expect("invalid `NEW_TEXT_LEN` variable"))
|
||||||
|
.unwrap_or(10);
|
||||||
|
|
||||||
|
let old = util::RandomCharIter::new(&mut rng)
|
||||||
|
.take(old_text_len)
|
||||||
|
.collect::<String>();
|
||||||
|
log::info!("old text: {:?}", old);
|
||||||
|
|
||||||
|
let mut diff = Diff::new(old.clone());
|
||||||
|
let mut hunks = Vec::new();
|
||||||
|
let mut new_len = 0;
|
||||||
|
let mut new = String::new();
|
||||||
|
while new_len < new_text_len {
|
||||||
|
let new_chunk_len = rng.gen_range(1..=new_text_len - new_len);
|
||||||
|
let new_chunk = util::RandomCharIter::new(&mut rng)
|
||||||
|
.take(new_len)
|
||||||
|
.collect::<String>();
|
||||||
|
log::info!("new chunk: {:?}", new_chunk);
|
||||||
|
new_len += new_chunk_len;
|
||||||
|
new.push_str(&new_chunk);
|
||||||
|
let new_hunks = diff.push_new(&new_chunk);
|
||||||
|
log::info!("hunks: {:?}", new_hunks);
|
||||||
|
hunks.extend(new_hunks);
|
||||||
|
}
|
||||||
|
let final_hunks = diff.finish();
|
||||||
|
log::info!("final hunks: {:?}", final_hunks);
|
||||||
|
hunks.extend(final_hunks);
|
||||||
|
|
||||||
|
log::info!("new text: {:?}", new);
|
||||||
|
let mut old_ix = 0;
|
||||||
|
let mut new_ix = 0;
|
||||||
|
let mut patched = String::new();
|
||||||
|
for hunk in hunks {
|
||||||
|
match hunk {
|
||||||
|
Hunk::Keep { len } => {
|
||||||
|
assert_eq!(&old[old_ix..old_ix + len], &new[new_ix..new_ix + len]);
|
||||||
|
patched.push_str(&old[old_ix..old_ix + len]);
|
||||||
|
old_ix += len;
|
||||||
|
new_ix += len;
|
||||||
|
}
|
||||||
|
Hunk::Remove { len } => {
|
||||||
|
old_ix += len;
|
||||||
|
}
|
||||||
|
Hunk::Insert { text } => {
|
||||||
|
assert_eq!(text, &new[new_ix..new_ix + text.len()]);
|
||||||
|
patched.push_str(&text);
|
||||||
|
new_ix += text.len();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
assert_eq!(patched, new);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -78,15 +78,14 @@ impl RefactoringAssistant {
|
||||||
}
|
}
|
||||||
|
|
||||||
let hunks = diff.push_new(&new_text);
|
let hunks = diff.push_new(&new_text);
|
||||||
hunks_tx.send((hunks, new_text)).await?;
|
hunks_tx.send(hunks).await?;
|
||||||
}
|
}
|
||||||
|
hunks_tx.send(diff.finish()).await?;
|
||||||
hunks_tx.send((diff.finish(), String::new())).await?;
|
|
||||||
|
|
||||||
anyhow::Ok(())
|
anyhow::Ok(())
|
||||||
});
|
});
|
||||||
|
|
||||||
while let Some((hunks, new_text)) = hunks_rx.next().await {
|
while let Some(hunks) = hunks_rx.next().await {
|
||||||
editor.update(&mut cx, |editor, cx| {
|
editor.update(&mut cx, |editor, cx| {
|
||||||
editor.buffer().update(cx, |buffer, cx| {
|
editor.buffer().update(cx, |buffer, cx| {
|
||||||
buffer.start_transaction(cx);
|
buffer.start_transaction(cx);
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue