@@ -1,6 +1,7 @@
11use std::ops::RangeInclusive;
22
33use helix_core::diagnostic::Severity;
4+use helix_term::application::Application;
45
56use super::*;
67
@@ -133,3 +134,62 @@ async fn test_selection_duplication() -> anyhow::Result<()> {
133134 .await?;
134135 Ok(())
135136}
137+
138+#[tokio::test(flavor = "multi_thread")]
139+async fn test_goto_file_impl() -> anyhow::Result<()> {
140+ let file = tempfile::NamedTempFile::new()?;
141+
142+ fn match_paths(app: &Application, matches: Vec<&str>) -> usize {
143+ app.editor
144+ .documents()
145+ .filter_map(|d| d.path()?.file_name())
146+ .filter(|n| matches.iter().any(|m| *m == n.to_string_lossy()))
147+ .count()
148+ }
149+
150+ // Single selection
151+ test_key_sequence(
152+ &mut AppBuilder::new().with_file(file.path(), None).build()?,
153+ Some("ione.js<esc>%gf"),
154+ Some(&|app| {
155+ assert_eq!(1, match_paths(app, vec!["one.js"]));
156+ }),
157+ false,
158+ )
159+ .await?;
160+
161+ // Multiple selection
162+ test_key_sequence(
163+ &mut AppBuilder::new().with_file(file.path(), None).build()?,
164+ Some("ione.js<ret>two.js<esc>%<A-s>gf"),
165+ Some(&|app| {
166+ assert_eq!(2, match_paths(app, vec!["one.js", "two.js"]));
167+ }),
168+ false,
169+ )
170+ .await?;
171+
172+ // Cursor on first quote
173+ test_key_sequence(
174+ &mut AppBuilder::new().with_file(file.path(), None).build()?,
175+ Some("iimport 'one.js'<esc>B;gf"),
176+ Some(&|app| {
177+ assert_eq!(1, match_paths(app, vec!["one.js"]));
178+ }),
179+ false,
180+ )
181+ .await?;
182+
183+ // Cursor on last quote
184+ test_key_sequence(
185+ &mut AppBuilder::new().with_file(file.path(), None).build()?,
186+ Some("iimport 'one.js'<esc>bgf"),
187+ Some(&|app| {
188+ assert_eq!(1, match_paths(app, vec!["one.js"]));
189+ }),
190+ false,
191+ )
192+ .await?;
193+
194+ Ok(())
195+}