Skip to content

Commit f0343cb

Browse files
Rollup merge of rust-lang#48106 - QuietMisdreavus:teleporting-crates, r=GuillaumeGomez
rustdoc: move manual "extern crate" statements outside automatic "fn main"s in doctests Gated on rust-lang#48095 - I based the branch atop that so i could show off the change in one of its tests, the actual change in this PR is just the last commit There are a handful of unfortunate assumptions in the way rustdoc processes `extern crate` statements in doctests: 1. In the absence of an `extern crate` statement in the test, if the test also uses the local crate name, it will automatically insert an `extern crate cratename;` statement into the test. 2. If the doctest *does* include an `extern crate` statement, rustdoc will not automatically insert one, on the assumption that doing so would introduce a duplicate import. 3. If a doctest does not have the substring `fn main` outside a comment, rustdoc will wrap the whole doctest in a generated `fn main` so it can be compiled. In short, whenever you write a doctest like this... ```rust //! extern crate my_crate; //! my_crate::some_cool_thing(); ``` ...rustdoc will turn it into (something like) this: ```rust fn main() { extern crate my_crate; my_crate::some_cool_thing(); } ``` This creates issues when compiled, because now `my_crate` isn't even properly in scope! This forces people who want to have multiple crates in their doctests (or an explicit `extern crate` statement) to also manually include their own `fn main`, so rustdoc doesn't put their imports in the wrong place. This PR just taps into another processing step rustdoc does to doctests: Whenever you add an `#![inner_attribute]` to the beginning of a doctest, rustdoc will actually splice those out and put it before the generated `fn main`. Now, we can just do the same with `extern crate`s at the beginning, too, and get a much nicer experience. Now, the above example will be converted into this: ```rust extern crate my_crate; fn main() { my_crate::some_cool_thing(); } ```
2 parents aec6535 + d8d4c58 commit f0343cb

File tree

2 files changed

+5
-2
lines changed

2 files changed

+5
-2
lines changed

Diff for: src/librustc_resolve/diagnostics.rs

+2
Original file line numberDiff line numberDiff line change
@@ -325,6 +325,8 @@ Erroneous code example:
325325
extern crate core;
326326
327327
struct core;
328+
329+
fn main() {}
328330
```
329331
330332
There are two possible solutions:

Diff for: src/librustdoc/test.rs

+3-2
Original file line numberDiff line numberDiff line change
@@ -414,7 +414,8 @@ fn partition_source(s: &str) -> (String, String) {
414414
for line in s.lines() {
415415
let trimline = line.trim();
416416
let header = trimline.is_whitespace() ||
417-
trimline.starts_with("#![");
417+
trimline.starts_with("#![") ||
418+
trimline.starts_with("extern crate");
418419
if !header || after_header {
419420
after_header = true;
420421
after.push_str(line);
@@ -814,8 +815,8 @@ use asdf::qwop;
814815
assert_eq!(2+2, 4);";
815816
let expected =
816817
"#![allow(unused)]
817-
fn main() {
818818
extern crate asdf;
819+
fn main() {
819820
use asdf::qwop;
820821
assert_eq!(2+2, 4);
821822
}".to_string();

0 commit comments

Comments
 (0)