Skip to content

Commit

Permalink
Add imports_granularity="Item".
Browse files Browse the repository at this point in the history
This option splits all imports into their own `use` statement.
  • Loading branch information
msmorgan authored and calebcartwright committed Jan 21, 2021
1 parent fec65a6 commit e16d4f3
Show file tree
Hide file tree
Showing 6 changed files with 81 additions and 9 deletions.
17 changes: 16 additions & 1 deletion Configurations.md
Original file line number Diff line number Diff line change
Expand Up @@ -1710,7 +1710,7 @@ pub enum Foo {}
Merge together related imports based on their paths.

- **Default value**: `Preserve`
- **Possible values**: `Preserve`, `Crate`, `Module`
- **Possible values**: `Preserve`, `Crate`, `Module`, `Item`
- **Stable**: No

#### `Preserve` (default):
Expand Down Expand Up @@ -1749,6 +1749,21 @@ use foo::{a, b, c};
use qux::{h, i};
```

#### `Item`:

Flatten imports so that each has its own `use` statement.

```rust
use foo::a;
use foo::b;
use foo::b::f;
use foo::b::g;
use foo::c;
use foo::d::e;
use qux::h;
use qux::i;
```

## `merge_imports`

This option is deprecated. Use `imports_granularity = "Crate"` instead.
Expand Down
2 changes: 2 additions & 0 deletions src/config/options.rs
Original file line number Diff line number Diff line change
Expand Up @@ -128,6 +128,8 @@ pub enum ImportGranularity {
Crate,
/// Use one `use` statement per module.
Module,
/// Use one `use` statement per imported item.
Item,
}

#[config_type]
Expand Down
37 changes: 37 additions & 0 deletions src/formatting/imports.rs
Original file line number Diff line number Diff line change
Expand Up @@ -182,6 +182,24 @@ pub(crate) fn merge_use_trees(use_trees: Vec<UseTree>, merge_by: SharedPrefix) -
result
}

pub(crate) fn flatten_use_trees(use_trees: Vec<UseTree>) -> Vec<UseTree> {
use_trees
.into_iter()
.flat_map(UseTree::flatten)
.map(|mut tree| {
// If a path ends in `::self`, rewrite it to `::{self}`.
if let Some(UseSegment::Slf(..)) = tree.path.last() {
let self_segment = tree.path.pop().unwrap();
tree.path.push(UseSegment::List(vec![UseTree::from_path(
vec![self_segment],
DUMMY_SP,
)]));
}
tree
})
.collect()
}

impl fmt::Debug for UseTree {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
fmt::Display::fmt(self, f)
Expand Down Expand Up @@ -1068,6 +1086,25 @@ mod test {
);
}

#[test]
fn test_flatten_use_trees() {
assert_eq!(
flatten_use_trees(parse_use_trees!["foo::{a::{b, c}, d::e}"]),
parse_use_trees!["foo::a::b", "foo::a::c", "foo::d::e"]
);

assert_eq!(
flatten_use_trees(parse_use_trees!["foo::{self, a, b::{c, d}, e::*}"]),
parse_use_trees![
"foo::{self}",
"foo::a",
"foo::b::c",
"foo::b::d",
"foo::e::*"
]
);
}

#[test]
fn test_use_tree_flatten() {
assert_eq!(
Expand Down
15 changes: 7 additions & 8 deletions src/formatting/reorder.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ use rustc_ast::ast;
use rustc_span::{symbol::sym, Span};

use crate::config::{Config, GroupImportsTactic, ImportGranularity};
use crate::formatting::imports::UseSegment;
use crate::formatting::imports::{flatten_use_trees, UseSegment};
use crate::formatting::modules::{get_mod_inner_attrs, FileModMap};
use crate::formatting::{
imports::{merge_use_trees, UseTree},
Expand Down Expand Up @@ -228,15 +228,14 @@ fn rewrite_reorderable_or_regroupable_items(
for (item, list_item) in normalized_items.iter_mut().zip(list_items) {
item.list_item = Some(list_item.clone());
}
match context.config.imports_granularity() {
ImportGranularity::Crate => {
normalized_items = merge_use_trees(normalized_items, SharedPrefix::Crate)
}
normalized_items = match context.config.imports_granularity() {
ImportGranularity::Crate => merge_use_trees(normalized_items, SharedPrefix::Crate),
ImportGranularity::Module => {
normalized_items = merge_use_trees(normalized_items, SharedPrefix::Module)
merge_use_trees(normalized_items, SharedPrefix::Module)
}
ImportGranularity::Preserve => {}
}
ImportGranularity::Item => flatten_use_trees(normalized_items),
ImportGranularity::Preserve => normalized_items,
};

let mut regrouped_items = match context.config.group_imports() {
GroupImportsTactic::Preserve => vec![normalized_items],
Expand Down
6 changes: 6 additions & 0 deletions tests/source/imports_granularity_item.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
// rustfmt-imports_granularity: Item

use a::{b, c, d};
use a::{f::g, h::{i, j}};
use a::{l::{self, m, n::o, p::*}};
use a::q::{self};
13 changes: 13 additions & 0 deletions tests/target/imports_granularity_item.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
// rustfmt-imports_granularity: Item

use a::b;
use a::c;
use a::d;
use a::f::g;
use a::h::i;
use a::h::j;
use a::l::m;
use a::l::n::o;
use a::l::p::*;
use a::l::{self};
use a::q::{self};

0 comments on commit e16d4f3

Please sign in to comment.