aboutsummaryrefslogtreecommitdiff
path: root/crates
diff options
context:
space:
mode:
Diffstat (limited to 'crates')
-rw-r--r--crates/hir_ty/src/diagnostics.rs48
-rw-r--r--crates/hir_ty/src/diagnostics/expr.rs16
2 files changed, 48 insertions, 16 deletions
diff --git a/crates/hir_ty/src/diagnostics.rs b/crates/hir_ty/src/diagnostics.rs
index 6eaa1beb8..323c5f963 100644
--- a/crates/hir_ty/src/diagnostics.rs
+++ b/crates/hir_ty/src/diagnostics.rs
@@ -670,21 +670,49 @@ fn foo() { break; }
670 ); 670 );
671 } 671 }
672 672
673 // Register the required standard library types to make the tests work
674 fn add_filter_map_with_find_next_boilerplate(body: &str) -> String {
675 let prefix = r#"
676 //- /main.rs crate:main deps:core
677 use core::iter::Iterator;
678 use core::option::Option::{self, Some, None};
679 "#;
680 let suffix = r#"
681 //- /core/lib.rs crate:core
682 pub mod option {
683 pub enum Option<T> { Some(T), None }
684 }
685 pub mod iter {
686 pub trait Iterator {
687 type Item;
688 fn filter_map<B, F>(self, f: F) -> FilterMap where F: FnMut(Self::Item) -> Option<B> { FilterMap }
689 fn next(&mut self) -> Option<Self::Item>;
690 }
691 pub struct FilterMap {}
692 impl Iterator for FilterMap {
693 type Item = i32;
694 fn next(&mut self) -> i32 { 7 }
695 }
696 }
697 "#;
698 format!("{}{}{}", prefix, body, suffix)
699 }
700
673 #[test] 701 #[test]
674 fn replace_filter_map_next_with_find_map() { 702 fn replace_filter_map_next_with_find_map2() {
675 check_diagnostics( 703 check_diagnostics(&add_filter_map_with_find_next_boilerplate(
676 r#" 704 r#"
677 fn foo() { 705 fn foo() {
678 let m = [1, 2, 3].iter().filter_map(|x| if *x == 2 { Some (4) } else { None }).next(); 706 let m = [1, 2, 3].iter().filter_map(|x| if *x == 2 { Some (4) } else { None }).next();
679 //^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ replace filter_map(..).next() with find_map(..) 707 //^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ replace filter_map(..).next() with find_map(..)
680 } 708 }
681 "#, 709 "#,
682 ); 710 ));
683 } 711 }
684 712
685 #[test] 713 #[test]
686 fn replace_filter_map_next_with_find_map_no_diagnostic_without_next() { 714 fn replace_filter_map_next_with_find_map_no_diagnostic_without_next() {
687 check_diagnostics( 715 check_diagnostics(&add_filter_map_with_find_next_boilerplate(
688 r#" 716 r#"
689 fn foo() { 717 fn foo() {
690 let m = [1, 2, 3] 718 let m = [1, 2, 3]
@@ -693,12 +721,12 @@ fn foo() { break; }
693 .len(); 721 .len();
694 } 722 }
695 "#, 723 "#,
696 ); 724 ));
697 } 725 }
698 726
699 #[test] 727 #[test]
700 fn replace_filter_map_next_with_find_map_no_diagnostic_with_intervening_methods() { 728 fn replace_filter_map_next_with_find_map_no_diagnostic_with_intervening_methods() {
701 check_diagnostics( 729 check_diagnostics(&add_filter_map_with_find_next_boilerplate(
702 r#" 730 r#"
703 fn foo() { 731 fn foo() {
704 let m = [1, 2, 3] 732 let m = [1, 2, 3]
@@ -708,12 +736,12 @@ fn foo() { break; }
708 .len(); 736 .len();
709 } 737 }
710 "#, 738 "#,
711 ); 739 ));
712 } 740 }
713 741
714 #[test] 742 #[test]
715 fn replace_filter_map_next_with_find_map_no_diagnostic_if_not_in_chain() { 743 fn replace_filter_map_next_with_find_map_no_diagnostic_if_not_in_chain() {
716 check_diagnostics( 744 check_diagnostics(&add_filter_map_with_find_next_boilerplate(
717 r#" 745 r#"
718 fn foo() { 746 fn foo() {
719 let m = [1, 2, 3] 747 let m = [1, 2, 3]
@@ -722,6 +750,6 @@ fn foo() { break; }
722 let n = m.next(); 750 let n = m.next();
723 } 751 }
724 "#, 752 "#,
725 ); 753 ));
726 } 754 }
727} 755}
diff --git a/crates/hir_ty/src/diagnostics/expr.rs b/crates/hir_ty/src/diagnostics/expr.rs
index 16bbd48fb..d740b7265 100644
--- a/crates/hir_ty/src/diagnostics/expr.rs
+++ b/crates/hir_ty/src/diagnostics/expr.rs
@@ -2,7 +2,9 @@
2 2
3use std::sync::Arc; 3use std::sync::Arc;
4 4
5use hir_def::{AdtId, AssocItemId, DefWithBodyId, expr::Statement, path::path, resolver::HasResolver}; 5use hir_def::{
6 expr::Statement, path::path, resolver::HasResolver, AdtId, AssocItemId, DefWithBodyId,
7};
6use hir_expand::{diagnostics::DiagnosticSink, name}; 8use hir_expand::{diagnostics::DiagnosticSink, name};
7use rustc_hash::FxHashSet; 9use rustc_hash::FxHashSet;
8use syntax::{ast, AstPtr}; 10use syntax::{ast, AstPtr};
@@ -163,11 +165,13 @@ impl<'a, 'b> ExprValidator<'a, 'b> {
163 None => return, 165 None => return,
164 }; 166 };
165 let iterator_trait_items = &db.trait_data(iterator_trait_id).items; 167 let iterator_trait_items = &db.trait_data(iterator_trait_id).items;
166 let filter_map_function_id = match iterator_trait_items.iter().find(|item| item.0 == name![filter_map]) { 168 let filter_map_function_id =
167 Some((_, AssocItemId::FunctionId(id))) => id, 169 match iterator_trait_items.iter().find(|item| item.0 == name![filter_map]) {
168 _ => return, 170 Some((_, AssocItemId::FunctionId(id))) => id,
169 }; 171 _ => return,
170 let next_function_id = match iterator_trait_items.iter().find(|item| item.0 == name![next]) { 172 };
173 let next_function_id = match iterator_trait_items.iter().find(|item| item.0 == name![next])
174 {
171 Some((_, AssocItemId::FunctionId(id))) => id, 175 Some((_, AssocItemId::FunctionId(id))) => id,
172 _ => return, 176 _ => return,
173 }; 177 };