Skip to content

Commit

Permalink
wip: add a few tests
Browse files Browse the repository at this point in the history
  • Loading branch information
markxoe committed Jun 3, 2024
1 parent ece8611 commit 70f92ed
Show file tree
Hide file tree
Showing 6 changed files with 300 additions and 9 deletions.
48 changes: 48 additions & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -13,3 +13,4 @@ inquire = "0.7.5"
log = { version = "0.4.21", features = ["std"] }
regex = { version = "1.10.4", features = ["std"] }
serde = { version = "1.0.202", features = ["derive"] }
tempfile = "3.10.1"
61 changes: 61 additions & 0 deletions src/data/algorithm/bfs.rs
Original file line number Diff line number Diff line change
Expand Up @@ -50,3 +50,64 @@ pub fn find_shortest_path(start: i32, end: i32, links: &LinkMap) -> Option<Vec<i

None
}

mod test {
#[allow(unused_imports)]
use crate::{data::maps::link_map::LinkMap, indication::ProgressBuilder};

#[test]
fn direct_link() {
let link_map = LinkMap::new_with_progress(
vec![(1, 2), (1, 3), (3, 2)].into_iter().collect(),
ProgressBuilder::empty(),
);

let path = super::find_shortest_path(1, 2, &link_map);

assert_eq!(path, Some(vec![1, 2]));
}

#[test]
fn single_possibility() {
let link_map = LinkMap::new_with_progress(
vec![(1, 2), (1, 5), (2, 3), (2, 5), (3, 4), (3, 5)]
.into_iter()
.collect(),
ProgressBuilder::empty(),
);

let path = super::find_shortest_path(1, 4, &link_map);

assert_eq!(path, Some(vec![1, 2, 3, 4]));
}

#[test]
fn multiple_possibilities_one_shortest() {
// path over 1->2->3->4 and 1->5->4
let link_map = LinkMap::new_with_progress(
vec![(1, 2), (2, 3), (3, 4), (1, 5), (5, 4)]
.into_iter()
.collect(),
ProgressBuilder::empty(),
);

let path = super::find_shortest_path(1, 4, &link_map);

assert_eq!(path, Some(vec![1, 5, 4]));
}

#[test]
fn equal_length_uses_first_in_map() {
// path over 1->2->3->4 and 1->5->6->4
let link_map = LinkMap::new_with_progress(
vec![(1, 2), (2, 3), (3, 4), (1, 5), (5, 6), (6, 4)]
.into_iter()
.collect(),
ProgressBuilder::empty(),
);

let path = super::find_shortest_path(1, 4, &link_map);

assert_eq!(path, Some(vec![1, 2, 3, 4]));
}
}
21 changes: 16 additions & 5 deletions src/data/maps/link_map.rs
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,11 @@ impl LinkMap {

let (shrink_every, progress_every) = {
let links_count = links.len();
(links_count / 1000, links_count / 1000)
if links_count < 1000 {
(1, 1)
} else {
(links_count / 1000, links_count / 1000)
}
};

while let Some((from, to)) = links.pop_front() {
Expand All @@ -46,11 +50,18 @@ impl LinkMap {
LinkMap { forward: map }
}

pub fn new(links: VecDeque<LinkResolved>) -> LinkMap {
LinkMap::new_with_progress(links, ProgressBuilder::empty())
}

pub fn get(&self, from: i32) -> Option<&Vec<i32>> {
self.forward.get(&from)
}
}

#[test]
fn new_link_map() {
let links = VecDeque::from(vec![(1, 2), (1, 3), (3, 2)]);

let map = LinkMap::new_with_progress(links, ProgressBuilder::empty());

assert_eq!(map.get(1), Some(&vec![2, 3]));
assert_eq!(map.get(2), None);
assert_eq!(map.get(3), Some(&vec![2]));
}
128 changes: 124 additions & 4 deletions src/data/maps/page_map.rs
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ pub struct PageMap {
id_to_redirect: HashMap<i32, i32>,
}

#[derive(Debug, PartialEq)]
pub struct PageMapResult {
pub id: i32,
pub title: String,
Expand Down Expand Up @@ -61,10 +62,6 @@ impl PageMap {
}
}

pub fn new(pages: VecDeque<Page>, redirect: VecDeque<Redirect>) -> Self {
Self::new_internal(pages, redirect, ProgressBuilder::empty())
}

pub fn new_with_progress(
pages: VecDeque<Page>,
redirect: VecDeque<Redirect>,
Expand Down Expand Up @@ -113,3 +110,126 @@ impl PageMap {
Some(page)
}
}

#[test]
fn new_page_map() {
let pages = {
let pages = vec![
Page {
id: 1,
title: "Page 1".to_string(),
redirect: false,
},
Page {
id: 2,
title: "Page 2".to_string(),
redirect: false,
},
Page {
id: 3,
title: "Also Page 2".to_string(),
redirect: true,
},
];
VecDeque::from(pages)
};

let redirects = {
let redirects = vec![Redirect {
id: 3,
title: "Page 2".to_string(),
}];
VecDeque::from(redirects)
};

let map = PageMap::new_with_progress(pages, redirects, ProgressBuilder::empty());

assert_eq!(map.name_to_id("Page 1"), Some(1));
assert_eq!(map.name_to_id("Page 2"), Some(2));
assert_eq!(map.name_to_id("Also Page 2"), Some(3));

assert_eq!(map.id_to_name(1), Some("Page 1"));
assert_eq!(map.id_to_name(2), Some("Page 2"));
assert_eq!(map.id_to_name(3), Some("Also Page 2"));

assert_eq!(map.id_to_redirect(1), None);
assert_eq!(map.id_to_redirect(2), None);
assert_eq!(map.id_to_redirect(3), Some(2));

assert_eq!(
map.lookup_title("Page 1"),
Some(PageMapResult {
id: 1,
title: "Page 1".to_string(),
redirect: None
})
);
assert_eq!(
map.lookup_title("Page 2"),
Some(PageMapResult {
id: 2,
title: "Page 2".to_string(),
redirect: None
})
);
assert_eq!(
map.lookup_title("Also Page 2"),
Some(PageMapResult {
id: 3,
title: "Also Page 2".to_string(),
redirect: Some(2)
})
);

assert_eq!(
map.lookup_id(1),
Some(PageMapResult {
id: 1,
title: "Page 1".to_string(),
redirect: None
})
);
assert_eq!(
map.lookup_id(2),
Some(PageMapResult {
id: 2,
title: "Page 2".to_string(),
redirect: None
})
);
assert_eq!(
map.lookup_id(3),
Some(PageMapResult {
id: 3,
title: "Also Page 2".to_string(),
redirect: Some(2)
})
);

assert_eq!(
map.resolve_by_title("Page 1"),
Some(PageMapResult {
id: 1,
title: "Page 1".to_string(),
redirect: None
})
);

assert_eq!(
map.resolve_by_title("Page 2"),
Some(PageMapResult {
id: 2,
title: "Page 2".to_string(),
redirect: None
})
);

assert_eq!(
map.resolve_by_title("Also Page 2"),
Some(PageMapResult {
id: 2,
title: "Page 2".to_string(),
redirect: None
})
);
}
50 changes: 50 additions & 0 deletions src/data/parsers/common.rs
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,10 @@ where
C: Clone,
C: Send,
{
if threads < 2 {
panic!("Threads must be greater than or equal 2");
}

let (tx, rx) = crossbeam_channel::bounded(0);

let reader_thread = std::thread::spawn(move || {
Expand Down Expand Up @@ -91,3 +95,49 @@ where

output
}

mod test {
#[allow(unused_imports)]
use std::{
env::temp_dir,
io::Write,
sync::{Arc, Mutex},
};

#[test]
fn all_lines_are_read() {
let dir = temp_dir();
let file_path = dir.join("test.txt");

// create file
{
let file = std::fs::File::create(&file_path).expect("Unable to create file");
let mut writer = std::io::BufWriter::new(file);
for i in 0..1000 {
writeln!(writer, "{}", i).expect("Unable to write to file");
}
}

let call_count = Arc::new(Mutex::new(0));

// parse file
let result = super::parse_file_async(
file_path.to_str().unwrap().to_string(),
2,
|line, ctx| {
*ctx.lock().unwrap() += 1;
vec![line.parse::<i32>().unwrap()]
},
call_count.clone(),
);

// check that all lines are read
assert_eq!(result.len(), 1000);
for i in 0..1000 {
assert!(result.contains(&i));
}

// check parser call count
assert_eq!(*call_count.lock().unwrap(), 1000);
}
}

0 comments on commit 70f92ed

Please sign in to comment.