diff options
author | Seivan Heidari <[email protected]> | 2019-10-31 08:43:20 +0000 |
---|---|---|
committer | Seivan Heidari <[email protected]> | 2019-10-31 08:43:20 +0000 |
commit | 8edda0e7b164009d6c03bb3d4be603fb38ad2e2a (patch) | |
tree | 744cf81075d394e2f9c06afb07642a2601800dda /crates/ra_syntax/src | |
parent | 49562d36b97ddde34cf7585a8c2e8f232519b657 (diff) | |
parent | d067afb064a7fa67b172abf561b7d80740cd6f18 (diff) |
Merge branch 'master' into feature/themes
Diffstat (limited to 'crates/ra_syntax/src')
-rw-r--r-- | crates/ra_syntax/src/ast.rs | 24 | ||||
-rw-r--r-- | crates/ra_syntax/src/ast/make.rs | 6 | ||||
-rw-r--r-- | crates/ra_syntax/src/ast/traits.rs | 19 | ||||
-rw-r--r-- | crates/ra_syntax/src/lib.rs | 14 |
4 files changed, 51 insertions, 12 deletions
diff --git a/crates/ra_syntax/src/ast.rs b/crates/ra_syntax/src/ast.rs index 1b2ce921a..a12da5be2 100644 --- a/crates/ra_syntax/src/ast.rs +++ b/crates/ra_syntax/src/ast.rs | |||
@@ -173,7 +173,7 @@ fn test_doc_comment_single_line_block_strips_suffix_whitespace() { | |||
173 | .ok() | 173 | .ok() |
174 | .unwrap(); | 174 | .unwrap(); |
175 | let module = file.syntax().descendants().find_map(Module::cast).unwrap(); | 175 | let module = file.syntax().descendants().find_map(Module::cast).unwrap(); |
176 | assert_eq!("this is mod foo", module.doc_comment_text().unwrap()); | 176 | assert_eq!("this is mod foo ", module.doc_comment_text().unwrap()); |
177 | } | 177 | } |
178 | 178 | ||
179 | #[test] | 179 | #[test] |
@@ -191,7 +191,27 @@ fn test_doc_comment_multi_line_block_strips_suffix() { | |||
191 | .ok() | 191 | .ok() |
192 | .unwrap(); | 192 | .unwrap(); |
193 | let module = file.syntax().descendants().find_map(Module::cast).unwrap(); | 193 | let module = file.syntax().descendants().find_map(Module::cast).unwrap(); |
194 | assert_eq!(" this\n is\n mod foo", module.doc_comment_text().unwrap()); | 194 | assert_eq!( |
195 | " this\n is\n mod foo\n ", | ||
196 | module.doc_comment_text().unwrap() | ||
197 | ); | ||
198 | } | ||
199 | |||
200 | #[test] | ||
201 | fn test_comments_preserve_trailing_whitespace() { | ||
202 | let file = SourceFile::parse( | ||
203 | r#" | ||
204 | /// Representation of a Realm. | ||
205 | /// In the specification these are called Realm Records. | ||
206 | struct Realm {}"#, | ||
207 | ) | ||
208 | .ok() | ||
209 | .unwrap(); | ||
210 | let def = file.syntax().descendants().find_map(StructDef::cast).unwrap(); | ||
211 | assert_eq!( | ||
212 | "Representation of a Realm. \nIn the specification these are called Realm Records.", | ||
213 | def.doc_comment_text().unwrap() | ||
214 | ); | ||
195 | } | 215 | } |
196 | 216 | ||
197 | #[test] | 217 | #[test] |
diff --git a/crates/ra_syntax/src/ast/make.rs b/crates/ra_syntax/src/ast/make.rs index 00422ea91..3d5f18bfa 100644 --- a/crates/ra_syntax/src/ast/make.rs +++ b/crates/ra_syntax/src/ast/make.rs | |||
@@ -77,7 +77,7 @@ pub fn tuple_struct_pat( | |||
77 | 77 | ||
78 | pub fn record_pat(path: ast::Path, pats: impl Iterator<Item = ast::Pat>) -> ast::RecordPat { | 78 | pub fn record_pat(path: ast::Path, pats: impl Iterator<Item = ast::Pat>) -> ast::RecordPat { |
79 | let pats_str = pats.map(|p| p.syntax().to_string()).join(", "); | 79 | let pats_str = pats.map(|p| p.syntax().to_string()).join(", "); |
80 | return from_text(&format!("{}{{ {} }}", path.syntax(), pats_str)); | 80 | return from_text(&format!("{} {{ {} }}", path.syntax(), pats_str)); |
81 | 81 | ||
82 | fn from_text(text: &str) -> ast::RecordPat { | 82 | fn from_text(text: &str) -> ast::RecordPat { |
83 | ast_from_text(&format!("fn f({}: ())", text)) | 83 | ast_from_text(&format!("fn f({}: ())", text)) |
@@ -129,11 +129,11 @@ pub fn where_clause(preds: impl Iterator<Item = ast::WherePred>) -> ast::WhereCl | |||
129 | } | 129 | } |
130 | 130 | ||
131 | pub fn if_expression(condition: &ast::Expr, statement: &str) -> ast::IfExpr { | 131 | pub fn if_expression(condition: &ast::Expr, statement: &str) -> ast::IfExpr { |
132 | return ast_from_text(&format!( | 132 | ast_from_text(&format!( |
133 | "fn f() {{ if !{} {{\n {}\n}}\n}}", | 133 | "fn f() {{ if !{} {{\n {}\n}}\n}}", |
134 | condition.syntax().text(), | 134 | condition.syntax().text(), |
135 | statement | 135 | statement |
136 | )); | 136 | )) |
137 | } | 137 | } |
138 | 138 | ||
139 | fn ast_from_text<N: AstNode>(text: &str) -> N { | 139 | fn ast_from_text<N: AstNode>(text: &str) -> N { |
diff --git a/crates/ra_syntax/src/ast/traits.rs b/crates/ra_syntax/src/ast/traits.rs index f275a4955..c2b005886 100644 --- a/crates/ra_syntax/src/ast/traits.rs +++ b/crates/ra_syntax/src/ast/traits.rs | |||
@@ -6,6 +6,7 @@ use itertools::Itertools; | |||
6 | 6 | ||
7 | use crate::{ | 7 | use crate::{ |
8 | ast::{self, child_opt, children, AstChildren, AstNode, AstToken}, | 8 | ast::{self, child_opt, children, AstChildren, AstNode, AstToken}, |
9 | match_ast, | ||
9 | syntax_node::{SyntaxElementChildren, SyntaxNodeChildren}, | 10 | syntax_node::{SyntaxElementChildren, SyntaxNodeChildren}, |
10 | }; | 11 | }; |
11 | 12 | ||
@@ -68,11 +69,12 @@ impl Iterator for ItemOrMacroIter { | |||
68 | fn next(&mut self) -> Option<ItemOrMacro> { | 69 | fn next(&mut self) -> Option<ItemOrMacro> { |
69 | loop { | 70 | loop { |
70 | let n = self.0.next()?; | 71 | let n = self.0.next()?; |
71 | if let Some(item) = ast::ModuleItem::cast(n.clone()) { | 72 | match_ast! { |
72 | return Some(ItemOrMacro::Item(item)); | 73 | match n { |
73 | } | 74 | ast::ModuleItem(it) => { return Some(ItemOrMacro::Item(it)) }, |
74 | if let Some(call) = ast::MacroCall::cast(n) { | 75 | ast::MacroCall(it) => { return Some(ItemOrMacro::Macro(it)) }, |
75 | return Some(ItemOrMacro::Macro(call)); | 76 | _ => {}, |
77 | } | ||
76 | } | 78 | } |
77 | } | 79 | } |
78 | } | 80 | } |
@@ -120,7 +122,7 @@ pub trait DocCommentsOwner: AstNode { | |||
120 | has_comments = true; | 122 | has_comments = true; |
121 | let prefix_len = comment.prefix().len(); | 123 | let prefix_len = comment.prefix().len(); |
122 | 124 | ||
123 | let line = comment.text().as_str(); | 125 | let line: &str = comment.text().as_str(); |
124 | 126 | ||
125 | // Determine if the prefix or prefix + 1 char is stripped | 127 | // Determine if the prefix or prefix + 1 char is stripped |
126 | let pos = | 128 | let pos = |
@@ -136,7 +138,10 @@ pub trait DocCommentsOwner: AstNode { | |||
136 | line.len() | 138 | line.len() |
137 | }; | 139 | }; |
138 | 140 | ||
139 | line[pos..end].trim_end().to_owned() | 141 | // Note that we do not trim the end of the line here |
142 | // since whitespace can have special meaning at the end | ||
143 | // of a line in markdown. | ||
144 | line[pos..end].to_owned() | ||
140 | }) | 145 | }) |
141 | .join("\n"); | 146 | .join("\n"); |
142 | 147 | ||
diff --git a/crates/ra_syntax/src/lib.rs b/crates/ra_syntax/src/lib.rs index c315ba552..5dcb6a95a 100644 --- a/crates/ra_syntax/src/lib.rs +++ b/crates/ra_syntax/src/lib.rs | |||
@@ -160,6 +160,20 @@ impl SourceFile { | |||
160 | } | 160 | } |
161 | } | 161 | } |
162 | 162 | ||
163 | /// Matches a `SyntaxNode` against an `ast` type. | ||
164 | /// | ||
165 | /// # Example: | ||
166 | /// | ||
167 | /// ```ignore | ||
168 | /// match_ast! { | ||
169 | /// match node { | ||
170 | /// ast::CallExpr(it) => { ... }, | ||
171 | /// ast::MethodCallExpr(it) => { ... }, | ||
172 | /// ast::MacroCall(it) => { ... }, | ||
173 | /// _ => None, | ||
174 | /// } | ||
175 | /// } | ||
176 | /// ``` | ||
163 | #[macro_export] | 177 | #[macro_export] |
164 | macro_rules! match_ast { | 178 | macro_rules! match_ast { |
165 | (match $node:ident { | 179 | (match $node:ident { |