File tree Expand file tree Collapse file tree 2 files changed +193
-0
lines changed 
crates/ide-completion/src Expand file tree Collapse file tree 2 files changed +193
-0
lines changed Original file line number Diff line number Diff line change @@ -1890,11 +1890,37 @@ fn is_in_breakable(node: &SyntaxNode) -> Option<(BreakableKind, SyntaxNode)> {
18901890} 
18911891
18921892fn  is_in_block ( node :  & SyntaxNode )  -> bool  { 
1893+     if  has_in_newline_expr_first ( node)  { 
1894+         return  true ; 
1895+     } ; 
18931896    node. parent ( ) 
18941897        . map ( |node| ast:: ExprStmt :: can_cast ( node. kind ( ) )  || ast:: StmtList :: can_cast ( node. kind ( ) ) ) 
18951898        . unwrap_or ( false ) 
18961899} 
18971900
1901+ /// Similar to `has_parens`, heuristic sensing incomplete statement before ambigiguous `Expr` 
1902+ /// 
1903+ /// Heuristic: 
1904+ /// 
1905+ /// If the `PathExpr` is left part of the `Expr` and there is a newline after the `PathExpr`, 
1906+ /// it is considered that the `PathExpr` is not part of the `Expr`. 
1907+ fn  has_in_newline_expr_first ( node :  & SyntaxNode )  -> bool  { 
1908+     if  ast:: PathExpr :: can_cast ( node. kind ( ) ) 
1909+         && let  Some ( NodeOrToken :: Token ( next) )  = node. next_sibling_or_token ( ) 
1910+         && next. kind ( )  == SyntaxKind :: WHITESPACE 
1911+         && next. text ( ) . contains ( '\n' ) 
1912+         && let  Some ( stmt_like)  = node
1913+             . ancestors ( ) 
1914+             . take_while ( |it| it. text_range ( ) . start ( )  == node. text_range ( ) . start ( ) ) 
1915+             . filter_map ( Either :: < ast:: ExprStmt ,  ast:: Expr > :: cast) 
1916+             . last ( ) 
1917+     { 
1918+         stmt_like. syntax ( ) . parent ( ) . and_then ( ast:: StmtList :: cast) . is_some ( ) 
1919+     }  else  { 
1920+         false 
1921+     } 
1922+ } 
1923+ 
18981924fn  next_non_trivia_token ( e :  impl  Into < SyntaxElement > )  -> Option < SyntaxToken >  { 
18991925    let  mut  token = match  e. into ( )  { 
19001926        SyntaxElement :: Node ( n)  => n. last_token ( ) ?, 
Original file line number Diff line number Diff line change @@ -2946,6 +2946,173 @@ fn let_in_let_chain() {
29462946    check_edit ( "let" ,  r#"fn f() { if true && $0 {} }"# ,  r#"fn f() { if true && let $1 = $0 {} }"# ) ; 
29472947} 
29482948
2949+ #[ test]  
2950+ fn  let_in_previous_line_of_ambiguous_expr ( )  { 
2951+     check_edit ( 
2952+         "let" , 
2953+         r#" 
2954+         fn f() { 
2955+             $0 
2956+             (1, 2).foo(); 
2957+         }"# , 
2958+         r#" 
2959+         fn f() { 
2960+             let $1 = $0; 
2961+             (1, 2).foo(); 
2962+         }"# , 
2963+     ) ; 
2964+ 
2965+     check_edit ( 
2966+         "let" , 
2967+         r#" 
2968+         fn f() { 
2969+             $0 
2970+             (1, 2) 
2971+         }"# , 
2972+         r#" 
2973+         fn f() { 
2974+             let $1 = $0; 
2975+             (1, 2) 
2976+         }"# , 
2977+     ) ; 
2978+ 
2979+     check_edit ( 
2980+         "let" , 
2981+         r#" 
2982+         fn f() -> i32 { 
2983+             $0 
2984+             -2 
2985+         }"# , 
2986+         r#" 
2987+         fn f() -> i32 { 
2988+             let $1 = $0; 
2989+             -2 
2990+         }"# , 
2991+     ) ; 
2992+ 
2993+     check_edit ( 
2994+         "let" , 
2995+         r#" 
2996+         fn f() -> [i32; 2] { 
2997+             $0 
2998+             [1, 2] 
2999+         }"# , 
3000+         r#" 
3001+         fn f() -> [i32; 2] { 
3002+             let $1 = $0; 
3003+             [1, 2] 
3004+         }"# , 
3005+     ) ; 
3006+ 
3007+     check_edit ( 
3008+         "let" , 
3009+         r#" 
3010+         fn f() -> [u8; 2] { 
3011+             $0 
3012+             *b"01" 
3013+         }"# , 
3014+         r#" 
3015+         fn f() -> [u8; 2] { 
3016+             let $1 = $0; 
3017+             *b"01" 
3018+         }"# , 
3019+     ) ; 
3020+ 
3021+     check ( 
3022+         r#" 
3023+         fn foo() { 
3024+             $0 
3025+             *b"01" 
3026+         }"# , 
3027+         expect ! [ [ r#" 
3028+             fn foo()  fn() 
3029+             bt u32     u32 
3030+             kw async 
3031+             kw const 
3032+             kw crate:: 
3033+             kw enum 
3034+             kw extern 
3035+             kw false 
3036+             kw fn 
3037+             kw for 
3038+             kw if 
3039+             kw if let 
3040+             kw impl 
3041+             kw impl for 
3042+             kw let 
3043+             kw letm 
3044+             kw loop 
3045+             kw match 
3046+             kw mod 
3047+             kw return 
3048+             kw self:: 
3049+             kw static 
3050+             kw struct 
3051+             kw trait 
3052+             kw true 
3053+             kw type 
3054+             kw union 
3055+             kw unsafe 
3056+             kw use 
3057+             kw while 
3058+             kw while let 
3059+             sn macro_rules 
3060+             sn pd 
3061+             sn ppd 
3062+         "# ] ] , 
3063+     ) ; 
3064+ 
3065+     check ( 
3066+         r#" 
3067+         fn foo() { 
3068+             match $0 {} 
3069+         }"# , 
3070+         expect ! [ [ r#" 
3071+             fn foo() fn() 
3072+             bt u32    u32 
3073+             kw const 
3074+             kw crate:: 
3075+             kw false 
3076+             kw for 
3077+             kw if 
3078+             kw if let 
3079+             kw loop 
3080+             kw match 
3081+             kw return 
3082+             kw self:: 
3083+             kw true 
3084+             kw unsafe 
3085+             kw while 
3086+             kw while let 
3087+         "# ] ] , 
3088+     ) ; 
3089+ 
3090+     check ( 
3091+         r#" 
3092+         fn foo() { 
3093+             $0 *b"01" 
3094+         }"# , 
3095+         expect ! [ [ r#" 
3096+             fn foo() fn() 
3097+             bt u32    u32 
3098+             kw const 
3099+             kw crate:: 
3100+             kw false 
3101+             kw for 
3102+             kw if 
3103+             kw if let 
3104+             kw loop 
3105+             kw match 
3106+             kw return 
3107+             kw self:: 
3108+             kw true 
3109+             kw unsafe 
3110+             kw while 
3111+             kw while let 
3112+         "# ] ] , 
3113+     ) ; 
3114+ } 
3115+ 
29493116#[ test]  
29503117fn  private_inherent_and_public_trait ( )  { 
29513118    check ( 
 
 
   
 
     
   
   
          
    
    
     
    
      
     
     
    You can’t perform that action at this time.
  
 
    
  
    
      
        
     
       
      
     
   
 
    
    
  
 
  
 
     
    
0 commit comments