Auto merge of #17228 - Veykril:stable-runnables-order, r=Veykril

internal: Sort computed runnables

Fixes https://github.com/rust-lang/rust-analyzer/issues/17223
This commit is contained in:
bors 2024-05-14 10:35:10 +00:00
commit d580944f7e

View File

@ -15,6 +15,7 @@
FxHashMap, FxHashSet, RootDatabase, SymbolKind, FxHashMap, FxHashSet, RootDatabase, SymbolKind,
}; };
use itertools::Itertools; use itertools::Itertools;
use span::TextSize;
use stdx::{always, format_to}; use stdx::{always, format_to};
use syntax::{ use syntax::{
ast::{self, AstNode}, ast::{self, AstNode},
@ -48,16 +49,15 @@ fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
#[derive(Debug, Clone, Hash, PartialEq, Eq)] #[derive(Debug, Clone, Hash, PartialEq, Eq)]
pub enum RunnableKind { pub enum RunnableKind {
Test { test_id: TestId, attr: TestAttr },
TestMod { path: String }, TestMod { path: String },
Test { test_id: TestId, attr: TestAttr },
Bench { test_id: TestId }, Bench { test_id: TestId },
DocTest { test_id: TestId }, DocTest { test_id: TestId },
Bin, Bin,
} }
#[cfg(test)] #[derive(Debug, Clone, Hash, PartialEq, Eq, PartialOrd, Ord)]
#[derive(Debug, Clone, Hash, PartialEq, Eq)] enum RunnableDiscKind {
enum RunnableTestKind {
Test, Test,
TestMod, TestMod,
DocTest, DocTest,
@ -65,6 +65,18 @@ enum RunnableTestKind {
Bin, Bin,
} }
impl RunnableKind {
fn disc(&self) -> RunnableDiscKind {
match self {
RunnableKind::TestMod { .. } => RunnableDiscKind::TestMod,
RunnableKind::Test { .. } => RunnableDiscKind::Test,
RunnableKind::DocTest { .. } => RunnableDiscKind::DocTest,
RunnableKind::Bench { .. } => RunnableDiscKind::Bench,
RunnableKind::Bin => RunnableDiscKind::Bin,
}
}
}
impl Runnable { impl Runnable {
// test package::module::testname // test package::module::testname
pub fn label(&self, target: Option<String>) -> String { pub fn label(&self, target: Option<String>) -> String {
@ -97,17 +109,6 @@ pub fn title(&self) -> String {
s.push_str(suffix); s.push_str(suffix);
s s
} }
#[cfg(test)]
fn test_kind(&self) -> RunnableTestKind {
match &self.kind {
RunnableKind::TestMod { .. } => RunnableTestKind::TestMod,
RunnableKind::Test { .. } => RunnableTestKind::Test,
RunnableKind::DocTest { .. } => RunnableTestKind::DocTest,
RunnableKind::Bench { .. } => RunnableTestKind::Bench,
RunnableKind::Bin => RunnableTestKind::Bin,
}
}
} }
// Feature: Run // Feature: Run
@ -193,6 +194,20 @@ pub(crate) fn runnables(db: &RootDatabase, file_id: FileId) -> Vec<Runnable> {
r r
}) })
})); }));
res.sort_by(|Runnable { nav, kind, .. }, Runnable { nav: nav_b, kind: kind_b, .. }| {
// full_range.start < focus_range.start < name, should give us a decent unique ordering
nav.full_range
.start()
.cmp(&nav_b.full_range.start())
.then_with(|| {
let t_0 = || TextSize::from(0);
nav.focus_range
.map_or_else(t_0, |it| it.start())
.cmp(&nav_b.focus_range.map_or_else(t_0, |it| it.start()))
})
.then_with(|| kind.disc().cmp(&kind_b.disc()))
.then_with(|| nav.name.cmp(&nav_b.name))
});
res res
} }
@ -571,13 +586,12 @@ mod tests {
fn check(ra_fixture: &str, expect: Expect) { fn check(ra_fixture: &str, expect: Expect) {
let (analysis, position) = fixture::position(ra_fixture); let (analysis, position) = fixture::position(ra_fixture);
let mut runnables = analysis.runnables(position.file_id).unwrap(); let result = analysis
runnables.sort_by_key(|it| (it.nav.full_range.start(), it.nav.name.clone())); .runnables(position.file_id)
.unwrap()
let result = runnables
.into_iter() .into_iter()
.map(|runnable| { .map(|runnable| {
let mut a = format!("({:?}, {:?}", runnable.test_kind(), runnable.nav); let mut a = format!("({:?}, {:?}", runnable.kind.disc(), runnable.nav);
if runnable.use_name_in_title { if runnable.use_name_in_title {
a.push_str(", true"); a.push_str(", true");
} }