* Fix #1120 - rework how the use list prefix is determined. * Added test commentary & another test case
This commit is contained in:
parent
9ed9618f1c
commit
4029b0e704
@ -16,7 +16,7 @@ use lists::{write_list, itemize_list, ListItem, ListFormatting, SeparatorTactic,
|
||||
use types::rewrite_path;
|
||||
use rewrite::{Rewrite, RewriteContext};
|
||||
use visitor::FmtVisitor;
|
||||
use std::cmp::Ordering;
|
||||
use std::cmp::{self, Ordering};
|
||||
|
||||
use syntax::{ast, ptr};
|
||||
|
||||
@ -159,29 +159,46 @@ impl Rewrite for ast::ViewPath {
|
||||
|
||||
impl<'a> FmtVisitor<'a> {
|
||||
pub fn format_imports(&mut self, use_items: &[ptr::P<ast::Item>]) {
|
||||
let mut last_pos = use_items.first()
|
||||
.and_then(|p_i| p_i.span.lo.0.checked_sub(1))
|
||||
.map(|span_lo| BytePos(span_lo))
|
||||
// Find the location immediately before the first use item in the run. This must not lie
|
||||
// before the current `self.last_pos`
|
||||
let pos_before_first_use_item = use_items.first()
|
||||
.map(|p_i| cmp::max(self.last_pos, p_i.span.lo))
|
||||
.unwrap_or(self.last_pos);
|
||||
let prefix = codemap::mk_sp(self.last_pos, last_pos);
|
||||
// Construct a list of pairs, each containing a `use` item and the start of span before
|
||||
// that `use` item.
|
||||
let mut last_pos_of_prev_use_item = pos_before_first_use_item;
|
||||
let mut ordered_use_items = use_items.iter()
|
||||
.map(|p_i| {
|
||||
let new_item = (&*p_i, last_pos);
|
||||
last_pos = p_i.span.hi;
|
||||
let new_item = (&*p_i, last_pos_of_prev_use_item);
|
||||
last_pos_of_prev_use_item = p_i.span.hi;
|
||||
new_item
|
||||
})
|
||||
.collect::<Vec<_>>();
|
||||
let pos_after_last_use_item = last_pos_of_prev_use_item;
|
||||
// Order the imports by view-path & other import path properties
|
||||
ordered_use_items.sort_by(|a, b| compare_use_items(a.0, b.0).unwrap());
|
||||
// First, output the span before the first import
|
||||
self.format_missing(prefix.hi);
|
||||
// Look for indent (the line part preceding the use is all whitespace) and excise that
|
||||
// from the prefix
|
||||
let prev_span_str = self.snippet(codemap::mk_sp(self.last_pos, pos_before_first_use_item));
|
||||
let span_end = match prev_span_str.rfind('\n') {
|
||||
Some(offset) => {
|
||||
if prev_span_str[offset..].trim().is_empty() {
|
||||
self.last_pos + BytePos(offset as u32)
|
||||
} else {
|
||||
pos_before_first_use_item
|
||||
}
|
||||
}
|
||||
None => pos_before_first_use_item,
|
||||
};
|
||||
self.format_missing(span_end);
|
||||
for ordered in ordered_use_items {
|
||||
// Fake out the formatter by setting `self.last_pos` to the appropriate location before
|
||||
// each item before visiting it.
|
||||
self.last_pos = ordered.1;
|
||||
self.visit_item(&ordered.0);
|
||||
}
|
||||
self.last_pos = last_pos;
|
||||
self.last_pos = pos_after_last_use_item;
|
||||
}
|
||||
|
||||
pub fn format_import(&mut self, vis: &ast::Visibility, vp: &ast::ViewPath, span: Span) {
|
||||
|
9
tests/source/issue-1120.rs
Normal file
9
tests/source/issue-1120.rs
Normal file
@ -0,0 +1,9 @@
|
||||
// rustfmt-reorder_imports: true
|
||||
|
||||
// Ensure that a use at the start of an inline module is correctly formatted.
|
||||
mod foo {use bar;}
|
||||
|
||||
// Ensure that an indented `use` gets the correct indentation.
|
||||
mod foo {
|
||||
use bar;
|
||||
}
|
11
tests/target/issue-1120.rs
Normal file
11
tests/target/issue-1120.rs
Normal file
@ -0,0 +1,11 @@
|
||||
// rustfmt-reorder_imports: true
|
||||
|
||||
// Ensure that a use at the start of an inline module is correctly formatted.
|
||||
mod foo {
|
||||
use bar;
|
||||
}
|
||||
|
||||
// Ensure that an indented `use` gets the correct indentation.
|
||||
mod foo {
|
||||
use bar;
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user