Join GitHub today
GitHub is home to over 31 million developers working together to host and review code, manage projects, and build software together.
Sign upRFC: Clarify and streamline paths and visibility #2126
Conversation
cramertj
added
the
Ergonomics Initiative
label
Aug 25, 2017
This comment has been minimized.
This comment has been minimized.
|
Once again, thanks so much to @aturon and everyone involved here for continuing to push on this! I was personaly quite happy with the previous iteration so it's only natural that I'm also quite happy with this version! This version of the RFC persists my favorite feature from before, requiring a keyword for local crate imports. It also allows obvious-in-retrospect things like I'd primarily like to advocate for the RFC 2088-like approach to the Otherwise I've got a few high-level comments but they're relatively nit-picky, so I don't mind resolving many of them during the implementation phase!
|
cramertj
referenced this pull request
Aug 25, 2017
Closed
Automatically Usable External Crates #2088
This comment has been minimized.
This comment has been minimized.
|
Huge I want to thank @cramertj, @withoutboats and @aturon for their awesome work in making this RFC happen. |
This comment has been minimized.
This comment has been minimized.
Under the RFC as-is, I think the replacement would be something like this: #![no_std]
#[cfg(feature = "std")]
crate use std;
fn main() {
// in some other cfg'd code:
let foo = crate::std::boxed::Box::new(5);
}Edit: note, though, that you probably wouldn't need this. Just writing the following would conditionally import #![no_std]
#[cfg(feature = "std")]
mod my_mod {
use std::<something>;
}Edit 2: I'm seeing lots of "confused" reactions-- can someone respond and explain what is confusing here? The idea is to import the |
vadimcn
reviewed
Aug 25, 2017
| - Second, one benefit of `crate` is that it helps reduce confusion about paths | ||
| appearing in `use` versus references to names elsewhere. In particular, it | ||
| serves as a reminder that `use` paths are absolute. | ||
|
|
This comment has been minimized.
This comment has been minimized.
vadimcn
Aug 25, 2017
•
Contributor
Another alternative might be to improve error messages.
Using example from Motivation, rather than just saying "Use of undeclared type or module futures", as rustc does now, it could add a note to the effect of "...but I did find an extern crate of this name. You can use an absolute path to refer to it as ::futures::Poll, or you can bring it into the current scope with use futures;".
This comment has been minimized.
This comment has been minimized.
est31
Aug 25, 2017
•
Contributor
The asymmetry between lib.rs and all other files doesn't just show up in the extern crate; declarations, it also appears when you do use std::mem; use mem::swap;. You can only do this in the crate root and as probably your first steps in Rust are by coding stuff inside the crate root and after that moving stuff from there into modules, it gives you this moment of surprise right at the start when you realize that submodules work differently. You can fix this inconsistency in two ways: either change how the crate root works, or change how use works to be always like the crate root, aka relative. Previous proposals wanted to do precisely this change to use, but I think this approach is nicer because its more conservative. Usually most of a crate's code is not inside lib.rs/main.rs.
This comment has been minimized.
This comment has been minimized.
vadimcn
Aug 26, 2017
•
Contributor
My point was that rather than revamping the module system, we could simply provide better error messages, like we do in other circumstances when the compiler can reasonably guess what went wrong. If we can't find module 'foo' in the current scope, but there is one in crate root, it's probably what the user wanted.
I don't think I've seen this option mentioned anywhere (at least lately). If it had been considered, maybe it should be mentioned among the alternatives along with why this isn't a good idea.
vadimcn
reviewed
Aug 25, 2017
|
|
||
| Another drawback is that imports from within your crate become more verbose, | ||
| since they require a leading `crate`. However, this downside is considerably | ||
| mitigated if [nesting in `use`] is permitted. |
This comment has been minimized.
This comment has been minimized.
vadimcn
Aug 25, 2017
Contributor
... or the compiler could search both the global namespace and the crate root (for relative use's only, use ::... would still be absolute).
cramertj
added
the
T-lang
label
Aug 25, 2017
This comment has been minimized.
This comment has been minimized.
DevOrc
commented
Aug 25, 2017
•
|
I have been loosely following these different proposals and none of them really got me excited. However this feels like a great compromise! Nice job! Nice job @aturon, @withoutboats, and @cramertj! |
This comment has been minimized.
This comment has been minimized.
ExpHP
commented
Aug 25, 2017
•
Really, everybody please do! Speaking as somebody who could barely even stand to hear the word "module" any more, I can attest that this proposal is different. It is short, has a single, clear focus, and will take maybe 5-8 minutes of your time to read through from start to finish. (I'm not sure; I should've used a stopwatch!) |
This comment has been minimized.
This comment has been minimized.
hawkw
commented
Aug 25, 2017
•
|
A huge thank-you to @aturon, @withoutboats, @cramertj, and everyone else who's worked on this series of RFCs – I know it's been an incredibly difficult process for so many people, but I'm really happy to see that it looks like we're close to reaching a compromise that seems acceptable both in improving the ergonomics story for beginners and not breaking existing code too drastically. Thank you all for your hard work! |
This comment has been minimized.
This comment has been minimized.
letheed
commented
Aug 25, 2017
|
I like it. Unlike most other proposals, I have no major reservation/pain point with this one. Looks like a clear improvement on all fronts to me. I'm happy about it, and kinda relieved to be honest (looking back on other proposals). It's been really hard to follow, so a big thank to all that worked on this for reaching this great consensus. |
This comment has been minimized.
This comment has been minimized.
arthurprs
commented
Aug 25, 2017
•
|
I'm not a fan of crate being used in the place of pub and the companion linter. I fail to see it bringing a net benefit. Edit: does the crate/pub also apply for struct fields? Overall this is great! A lot of those for all involved so far |
This comment has been minimized.
This comment has been minimized.
newpavlov
commented
Aug 25, 2017
•
|
Great work! Some comments and questions:
I don't think so, first without it we reduce need for fixing perfectly fine code, and second I personally like that to rename/move module you just need to rename/move folder and fix
I prefer What about inline modules? As I understand they will be left untouched?
In your example you forgot to add If possible I think ideal solution would be to allow use of use core::ops::Add;
#[cfg(feature = "std")]
use std::io::Read;And issue compilation errors if |
This comment has been minimized.
This comment has been minimized.
|
edit: nevermind, I forgot that epochs are explicit opt-in If I understand correctly, the second epoch requires migrating all There's probably a long tail of crates on crates.io that are not maintained. Are they going to be left broken? Forcefully |
This comment has been minimized.
This comment has been minimized.
The epochs system means that they will not break; they'd be on epoch 2015. |
This comment has been minimized.
This comment has been minimized.
|
@pornel Maybe I've missed something, but I thought a major highlight of the epochs proposal was that crates written for different epochs are fully intercompatible, so that abandoned crates for old epochs will |
This comment has been minimized.
This comment has been minimized.
nicoburns
commented
Aug 25, 2017
•
|
I think this is the right change. I would really like to see exploration of a closer mapping of modules to the filesystem. But I feel like doing that cleanly may require removing I would also like to see some syntax sugar for crate/self/super: something to visually distinguish them from module identifiers like |
This comment has been minimized.
This comment has been minimized.
Rufflewind
commented
Aug 25, 2017
So I take this to mean that in Epoch 2 it will be possible to use an external library named |
This comment has been minimized.
This comment has been minimized.
Yes, that's the idea! And in particular, there's no way to get there without a new epoch. |
mark-i-m
reviewed
Aug 25, 2017
| ```rust | ||
| // Either of these work, because we brought `std` into scope: | ||
| fn make_vec() -> Vec<u8> { ... } | ||
| fn make_vec() -> std::vec::Vec<u8> { ... } |
This comment has been minimized.
This comment has been minimized.
mark-i-m
Aug 25, 2017
Contributor
Should the comment be
// Either of these work because we brought both `std` and `std::vec::Vec<u8>` into scope
?
aturon
reviewed
Aug 25, 2017
| ``` | ||
|
|
||
| All `use` declarations are interpreted as fully qualified paths, making the | ||
| leading `::` optional for them. |
This comment has been minimized.
This comment has been minimized.
aturon
Aug 25, 2017
Author
Member
Yes, the guide is describing how things will look under the full implementation, which means a future epoch.
mark-i-m
reviewed
Aug 25, 2017
|
|
||
| - Cargo will provide a new `alias` key for dependencies, so that e.g. users who | ||
| want to use the `rand` crate but call it `random` instead can now write `rand | ||
| = { version = "0.3", alias = "random" }`. |
This comment has been minimized.
This comment has been minimized.
mark-i-m
Aug 25, 2017
Contributor
Perhaps I'm missing something obvious, but how does rustc get this alias information? Does it get passed by cargo or does rustc parse the Cargo.toml? The RFC says that the interface between rustc and cargo doesn't change, so I'm a bit confused here...
This comment has been minimized.
This comment has been minimized.
eddyb
Aug 25, 2017
Member
Cargo already passes --extern rand=path/to/rand.rlib, all it has to do is change the first rand to be random, but the interface remains the same. Maybe the RFC should be more explicit here?
This comment has been minimized.
This comment has been minimized.
epdtry
Aug 25, 2017
It's not spelled out here, but in previous proposals, the idea was for cargo to pass --extern foo=.../libbar.rlib. This form of aliasing is already supported by rustc, so the only change is to let cargo make use of it.
This comment has been minimized.
This comment has been minimized.
mark-i-m
Aug 26, 2017
Contributor
Ah, that makes sense. Perhaps this could be added to the RFC, please, @aturon ?
This comment has been minimized.
This comment has been minimized.
Phrohdoh
commented
Aug 25, 2017
•
|
Just a quick question from me: This RFC states that Everything else looks fantastic and is what I had hoped for when I began reading and writing Rust. Edit: Actually, mostly everything looks good. I do not like implicitly bringing things into scope. |
aturon
referenced this pull request
Sep 17, 2017
Closed
Tracking issue for RFC 2126: Clarify and streamline paths and visibility #44660
aturon
merged commit 8248775
into
rust-lang:master
Sep 17, 2017
This comment has been minimized.
This comment has been minimized.
|
This RFC has now been merged! Thank you, all, for what has surely been the most extensive continuous design discussion in Rust history (considering the prior RFCs and internals threads). This discussion helped shape a huge number of iterations, and the final design is much stronger for it -- besides which, it is also appealing to a much wider array of stakeholders. And in particular, I believe that all major points that have been raised on the final design have been addressed, either through changes or discussion about the tradeoffs. As per recent comments, there are two formal Unresolved Questions left:
Discussion on those points will continue on the tracking issue. |
This comment has been minimized.
This comment has been minimized.
vitiral
commented
Sep 18, 2017
|
I have opened a new RFC to discuss |
carols10cents
referenced this pull request
Sep 22, 2017
Closed
RFC 2126: Clarify and streamline paths and visibility (modules) #41
This comment has been minimized.
This comment has been minimized.
|
I just realised that |
This comment has been minimized.
This comment has been minimized.
ExpHP
commented
Sep 23, 2017
Do you mean safety as in Privacy is an integral part of safety, no doubt about that; but I suspect that most usage of
Assuming you mean the |
This comment has been minimized.
This comment has been minimized.
Michael-F-Bryan
commented
Dec 22, 2017
|
@aturon, it looks like the "rendered" link in this issue's description is broken. Any chance you can update it? It looks like it's just a case of changing the placeholder |
This was referenced Dec 25, 2017
This comment has been minimized.
This comment has been minimized.
Lokathor
commented
Jan 9, 2018
|
@aturon your "rendered" link is unfortunately still broken |
This comment has been minimized.
This comment has been minimized.
|
@Lokathor Thanks for the reminder - I went ahead and fixed it. |
petrochenkov
referenced this pull request
Jan 10, 2018
Open
Make std available to proc macro root in phase 1 #47314
alexcrichton
referenced this pull request
Jan 17, 2018
Merged
Implement renaming dependencies in the manifest #4953
petrochenkov
referenced this pull request
Feb 4, 2018
Open
Should `use super::{self, ...}` work? #37156
jonhoo
referenced this pull request
Apr 11, 2018
Closed
Adding imports and main to first README example #10
This comment has been minimized.
This comment has been minimized.
dlukes
commented
Jul 22, 2018
|
I've been searching for that experimental RFC regarding "the possibility of determining modules from the file system" (as mentioned in OP) but can't find it anywhere... Any pointers, please? :) |
This comment has been minimized.
This comment has been minimized.
|
@dlukes I don't believe that particular facet ever got as far as an eRFC, only discussion. That may get revisited after the 2018 edition. |
This comment has been minimized.
This comment has been minimized.
dlukes
commented
Jul 22, 2018
|
@joshtriplett Oh OK, thanks :) Sorry, I guess this must've been discussed somewhere at some point, but as a newcomer to the discussion, it's a bit daunting to comb through the sheer volume of comments in the various threads devoted to the subject. @aturon Please maybe remove "The experimental RFC will be posted soon." from OP then, if you have a bit of spare time, so as not to confuse latecomers? :) In any case, thanks for the huge amount of intellectual and emotional energy you guys spent on this! For a casual user such as myself, it was fairly hard to translate the seemingly simple rules behind Rust's original module system into the right set of intuitions and habits. |
aturon commentedAug 25, 2017
•
edited by Centril
Read this first
This is the latest RFC in the ongoing saga around Rust's module system. For those of you who have stopped following due to fatigue😩 : this is almost certainly the final iteration, and I'd like to ask you one last time to take a fresh look -- almost all of the text here is new. ❤️
Relative to earlier discussion, this proposal is drastically more conservative. It does not include any changes to
mod(i.e., it does not propose to determine module structure from the file system). It does not require epochs.The lang team does still want to explore the possibility of determining modules from the file system, but plans to do that through an experimental RFC -- i.e., to seek just for consensus that we can land a prototype implementation to gather more data and experience; a full RFC must subsequently be accepted prior to any stabilization. The experimental RFC will be posted soon.
How to give feedback
A word about feedback. I'm eager for feedback from the entire community, but am also conscious that the comment velocity on this topic has been very large. Thus I would ask:
Summary
This RFC seeks to clarify and streamline Rust's story around paths and visibility for modules and crates. That story will look as follows:
craterefers to the current crate (other forms are linted, see below)extern crateis no longer necessary, and is linted (see below); dependencies are available at the root unless shadowed.cratekeyword also acts as a visibility modifier, equivalent to today'spub(crate). Consequently, uses of barepubon items that are not actually publicly exported are linted, suggestingcratevisibility instead.foo.rsandfoo/subdirectory may coexist;mod.rsis no longer needed when placing submodules in a subdirectory.These changes do not require a new epoch. The new features are purely additive. They can ship with allow-by-default lints, which can gradually be moved to warn-by-default and deny-by-default over time, as better tooling is developed and more code has actively made the switch.
This RFC incorporates some text written by @withoutboats and @cramertj, who have both been involved in the long-running discussions on this topic.
Rendered