Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add ExternalCrate import grouping style #5723

Open
wants to merge 2 commits into
base: master
Choose a base branch
from

Conversation

shepmaster
Copy link
Member

This creates two groups:

  1. std, core, alloc and external crates,
  2. self, super and crate imports.

@calebcartwright
Copy link
Member

Haven't looked at the proposed changes yet (and tbh it'll probably be a while before we can), but did want to go ahead and share that I'm generally receptive to incorporating this, and really any grouping style variant which is content with lumping all the things rustfmt can't deterministically recognize explicitly into an "other" bucket.

One ask would be to ensure that there's additional sets of tests that include different combinations of the import related configuration options as these can sometimes sneakily step on each other (e.g.imports_granularity and reorder_imports being the ones most likely needed to test against)

@shepmaster
Copy link
Member Author

I've added the tests I think you were looking for.

@calebcartwright
Copy link
Member

Apologies in advance for the bikeshed, but I feel like we'll want a better name than ExternalCrate since it's really more of a... the things we qualify as "Crate", and then everything else in the preceding group.

@ytmimi @fee1-dead do you have any thoughts/perspectives/suggested names?

@calebcartwright
Copy link
Member

Will add that the code and tests lgtm, so I'd be content trying to get this merged and into the next release if we can come to an agreement on the variant name

@calebcartwright calebcartwright added pr-waiting-on-author release-notes Needs an associated changelog entry and removed pr-not-reviewed labels Aug 13, 2023
Comment on lines +204 to +227
/// Divides imports into two groups, corresponding to external crates
/// and local imports. Sorts each subgroup.
fn group_imports_external_crate(uts: Vec<UseTree>) -> Vec<Vec<UseTree>> {
let mut external_imports = Vec::new();
let mut local_imports = Vec::new();

for ut in uts.into_iter() {
if ut.path.is_empty() {
external_imports.push(ut);
continue;
}
match &ut.path[0].kind {
UseSegmentKind::Ident(..) => external_imports.push(ut),
UseSegmentKind::Slf(_) | UseSegmentKind::Super(_) | UseSegmentKind::Crate(_) => {
local_imports.push(ut)
}
// These are probably illegal here
UseSegmentKind::Glob | UseSegmentKind::List(_) => external_imports.push(ut),
}
}

vec![external_imports, local_imports]
}

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There could be a way to deduplicate this and StdExternalCrate, by either calling group_imports_std_external_crate in this function or calling this function in the other function.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's been a while since I was in the code, but I have a vague recollection that there wasn't much that was useful to DRY up here. That being said, WDYT about something that results in:

    for ut in uts {
        match UseCategory::categorize(ut) {
            UseCategory::Std(ut) => std_imports.push(ut),
            UseCategory::External(ut) => external_imports.push(ut),
            UseCategory::Local(ut) => local_imports.push(ut),
        }
    }

and

    for ut in uts {
        match UseCategory::categorize(ut) {
            UseCategory::Std(ut) | UseCategory::External(ut) => external_imports.push(ut),
            UseCategory::Local(ut) => local_imports.push(ut),
        }
    }

@fee1-dead
Copy link
Member

I feel like we'll want a better name than ExternalCrate since it's really more of a... the things we qualify as "Crate", and then everything else in the preceding group.

The things we qualify as External excludes Std as given in the StdExternalCrate naming. But I can't really think of a word that replaces External..

@ytmimi
Copy link
Contributor

ytmimi commented Aug 17, 2023

Best I've ben able to come up with for now:

  • CrateAndNonCrate
  • NonCrateAndCrate
  • CrateEverythingElse
  • DependenciesCrate
  • CrateForeign

This creates two groups:

1. `std`, `core`, `alloc` and external crates,
2. `self`, `super` and `crate` imports.
@shepmaster
Copy link
Member Author

In my mind, I categorize it thusly:

(further details on Zulip)

So I'd probably prefer to call it something like MineOrNotMine or DependenciesNotDependencies

as given in the StdExternalCrate

At the risk of shooting myself in the bikeshed, is there a better naming scheme that we could switch to (leaving the current name as an alias for compatibility)? One thing I've found tricky is the lack of words in between the nouns.

As a introductory example that I have no attachment to, StdExternalCrate isn't quite as self-documenting as StdVsExternalVsCrate compared to StdAndExternalVsCrate.

@calebcartwright
Copy link
Member

Yeah I was going to mention that we can change the name of the other variant in a non-breaking way if switching to a different naming convention allows for us to more easily derive a name that works for the new style introduced here

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
release-notes Needs an associated changelog entry
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants