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

Support JSON with rustdoc. #5878

Merged
merged 2 commits into from
Aug 10, 2018
Merged

Support JSON with rustdoc. #5878

merged 2 commits into from
Aug 10, 2018

Conversation

ehuss
Copy link
Contributor

@ehuss ehuss commented Aug 9, 2018

This allows cargo doc --message-format=json to actually work.

Note that this explicitly does not attempt to support it for doctests for
several reasons:

  • rustdoc --test --error-format=json does not work for some reason.
  • Since the lib is usually compiled before running rustdoc, warnings/errors
    will be emitted correctly by rustc.
  • I'm unaware of any errors/warnings rustdoc --test is capable of producing
    assuming the code passed rustc.
  • The compilation of the tests themselves do not support JSON.
  • libtest does not output json, so it's utility is limited.

@rust-highfive
Copy link

r? @matklad

(rust_highfive has picked a reviewer for you, use r? to override)

This allows `cargo doc --message-format=json` to actually work.

Note that this explicitly does not attempt to support it for doctests for
several reasons:
- `rustdoc --test --error-format=json` does not work for some reason.
- Since the lib is usually compiled before running rustdoc, warnings/errors
  will be emitted correctly by rustc.
- I'm unaware of any errors/warnings `rustdoc --test` is capable of producing
  assuming the code passed `rustc`.
- The compilation of the tests themselves do not support JSON.
- libtest does not output json, so it's utility is limited.
@ehuss
Copy link
Contributor Author

ehuss commented Aug 9, 2018

cc @GuillaumeGomez I assume this is OK now that --error-format is stabilized?

@GuillaumeGomez
Copy link
Member

Indeed!

Copy link
Member

@matklad matklad left a comment

Choose a reason for hiding this comment

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

❤️

&mut json_stdout,
&mut |line| json_stderr(line, &package_id, &target),
false,
).map(drop)
Copy link
Member

Choose a reason for hiding this comment

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

map(drop) probably should not be here, it's just ignore the error. I wonder if the one on the next line should be removed as well?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Yea, it's a little weird. The intent is so that all branches are CargoResult<()> so they all have the same type so that a common error can be attached. I can't think of a more elegant way to do that.

Copy link
Member

Choose a reason for hiding this comment

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

Oh, I've misunderstood the intention of the code completely...

Yep, the only better way to write this would probably be a catch block, which is currently unstable.

Copy link
Member

Choose a reason for hiding this comment

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

You could go the other way and change rustdoc.exec() to rustdoc.exec_with_output(), so all branches type-check to CargoResult<Output>.

Copy link
Member

Choose a reason for hiding this comment

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

That'll unfortunately hide rustdoc's output from the user, b/c it would be captured.

Copy link
Member

Choose a reason for hiding this comment

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

Ah. I see.

@@ -999,3 +987,33 @@ impl Kind {
}
}
}

fn json_stdout(line: &str) -> CargoResult<()> {
Copy link
Member

@matklad matklad Aug 9, 2018

Choose a reason for hiding this comment

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

Let's rename this to assert_is_empty? EDIT: or smthing similar, so it's clear on the call site what actually happens with json on stdout :)

Copy link
Member

Choose a reason for hiding this comment

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

Also, are we sure that rustdoc's stdout is clear?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

I'll investigate if it is possible for it to print to stdout.

@@ -631,6 +605,10 @@ fn rustdoc<'a, 'cfg>(cx: &mut Context<'a, 'cfg>, unit: &Unit<'a>) -> CargoResult
rustdoc.arg("--cfg").arg(&format!("feature=\"{}\"", feat));
}

if bcx.build_config.json_messages() {
rustdoc.arg("--error-format").arg("json");
Copy link
Member

Choose a reason for hiding this comment

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

We don't need to feature-detect support for json here, right? The user requests --message-format=json explicitly, so they'll see an error and that is expected behavior.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

I don't understand the question. This is the code that translates cargo's --message-format flag to rustdoc's --error-format flag.

Copy link
Member

Choose a reason for hiding this comment

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

--error-format is a recent addition to rustdoc, so, in theory, using new cargo and old rustdoc could result in a

error: the `-Z unstable-options` flag must also be passed to enable the flag `error-format`

message. However, that should be fine, because the user has to ask for cargo doc --message-format=json explicitly. That is, it's not a flag that we add automatically for existing workflows, so we don't have to feature-detect support for it.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Oh, I understand now. Yea, my understanding is that the version of cargo is tightly wedded to rustc and rustdoc. I think some distributions have attempted to split them, but afaik cargo doesn't really support that use case, right? At least in this case, it wouldn't break the normal usage.

Copy link
Member

Choose a reason for hiding this comment

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

It is at least somewhat supported: you can override compiler & rustdoc with env vars, and we try account for different compilers in Rustc cache. I think the current approach is "don't break things without necessity", and I don't remember any actual CLI changes that could have caused breakage.

// This can be removed once 1.30 is stable (rustdoc --error-format stabilized).
return;
}
let p = project().file("src/lib.rs", "asdf").build();
Copy link
Member

Choose a reason for hiding this comment

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

Hm, let's use a code that is valid, but has docstring errors? That way, we'll be more sure that we are checking rustdoc output specifically.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Sure, I was on the fence with that. My concern is that the rustdoc messages might be a little unstable, but there is another test already doing that.

}

fn json_stderr(line: &str, package_id: &PackageId, target: &Target) -> CargoResult<()> {
// stderr from rustc/rustdoc can have a mix of JSON and non-JSON output
Copy link
Member

Choose a reason for hiding this comment

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

Hm, does rustdoc put JSON on stderr as well? It's a shame that Cargo and Rustc use different streams for JSON =/

Copy link
Contributor Author

Choose a reason for hiding this comment

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

It is an odd inconsistency. There's an open issue for that (rust-lang/rust#48301). I imagine since the vast majority of people use rustc behind cargo it doesn't really come up often.

@matklad
Copy link
Member

matklad commented Aug 9, 2018

LGTM!

Let's also see what @alexcrichton thinks about this, because formally this extend "public API" of Cargo.

@alexcrichton
Copy link
Member

@bors: r+

Thanks for this @ehuss!

I agree that we do not need to do feature detection here, while Cargo supports mismatched rustc it's like how Rustc supports other versions of LLVM. It sort of works but not if you want everything to work.

@bors
Copy link
Collaborator

bors commented Aug 10, 2018

📌 Commit c28823f has been approved by alexcrichton

@bors
Copy link
Collaborator

bors commented Aug 10, 2018

⌛ Testing commit c28823f with merge 578e253...

bors added a commit that referenced this pull request Aug 10, 2018
Support JSON with rustdoc.

This allows `cargo doc --message-format=json` to actually work.

Note that this explicitly does not attempt to support it for doctests for
several reasons:
- `rustdoc --test --error-format=json` does not work for some reason.
- Since the lib is usually compiled before running rustdoc, warnings/errors
  will be emitted correctly by rustc.
- I'm unaware of any errors/warnings `rustdoc --test` is capable of producing
  assuming the code passed `rustc`.
- The compilation of the tests themselves do not support JSON.
- libtest does not output json, so it's utility is limited.
@bors
Copy link
Collaborator

bors commented Aug 10, 2018

☀️ Test successful - status-appveyor, status-travis
Approved by: alexcrichton
Pushing 578e253 to master...

@bors bors merged commit c28823f into rust-lang:master Aug 10, 2018
bors added a commit to rust-lang/rust that referenced this pull request Aug 15, 2018
Update cargo

- Update transitioning url (rust-lang/cargo#5889)
- Resolve some clippy lint warnings (rust-lang/cargo#5884)
- Don't kill child processes on normal exit on Windows (rust-lang/cargo#5887)
- fix a bunch of clippy warnings (rust-lang/cargo#5876)
- Add support for rustc's --error-format short (rust-lang/cargo#5879)
- Support JSON with rustdoc. (rust-lang/cargo#5878)
- Fix rustfmt instructions in CONTRIBUTING.md (rust-lang/cargo#5880)
- Allow `cargo run` in workspaces. (rust-lang/cargo#5877)
- Change target filters in workspaces. (rust-lang/cargo#5873)
- Improve verbose console and log for finding git repo in package check (rust-lang/cargo#5858)
- Meta rename (rust-lang/cargo#5871)
- fetch: skip target tests when cross_compile is disabled (rust-lang/cargo#5870)
- Fully capture rustc and rustdoc output when -Zcompile-progress is passed (rust-lang/cargo#5862)
- Fix test --example docs. (rust-lang/cargo#5867)
- Add a feature to build a vendored OpenSSL (rust-lang/cargo#5865)
@ehuss ehuss added this to the 1.30.0 milestone Feb 6, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

7 participants