diff --git a/src/bin/cargo/commands/doc.rs b/src/bin/cargo/commands/doc.rs index 8405015dfbb..f7c688f414d 100644 --- a/src/bin/cargo/commands/doc.rs +++ b/src/bin/cargo/commands/doc.rs @@ -29,6 +29,14 @@ pub fn cli() -> App { .arg_target_dir() .arg_manifest_path() .arg_message_format() + .arg( + Arg::with_name("dep-mode") + .long("dep-mode") + .help("Configure the set of dependencies to document") + .takes_value(true) + .possible_values(&["dev", "normal", "all", "build"]) + .default_value("normal"), + ) .after_help( "\ By default the documentation for the local package and all dependencies is @@ -48,10 +56,29 @@ the `cargo help pkgid` command. pub fn exec(config: &mut Config, args: &ArgMatches<'_>) -> CliResult { let ws = args.workspace(config)?; - let mode = CompileMode::Doc { - deps: !args.is_present("no-deps"), + let dep_mode = if args.is_present("no-deps") { + DepDocMode::NoDeps + } else { + match args.value_of("dev") { + Some("dev") => DepDocMode::Development, + Some("all") => DepDocMode::All, + Some("build") => DepDocMode::Build, + _ => DepDocMode::Normal, + } }; + let mode = CompileMode::Doc { dep_mode }; let mut compile_opts = args.compile_options(config, mode, Some(&ws))?; + + if !config.cli_unstable().unstable_options + && dep_mode != DepDocMode::Normal + && dep_mode != DepDocMode::NoDeps + { + return Err(failure::format_err!( + "`cargo doc --dep-mode` is unstable, pass `-Z unstable-options` to enable it" + ) + .into()); + } + compile_opts.local_rustdoc_args = if args.is_present("document-private-items") { Some(vec!["--document-private-items".to_string()]) } else { diff --git a/src/bin/cargo/commands/rustdoc.rs b/src/bin/cargo/commands/rustdoc.rs index 6616dc70e18..3e676c6544d 100644 --- a/src/bin/cargo/commands/rustdoc.rs +++ b/src/bin/cargo/commands/rustdoc.rs @@ -53,7 +53,9 @@ pub fn exec(config: &mut Config, args: &ArgMatches<'_>) -> CliResult { let ws = args.workspace(config)?; let mut compile_opts = args.compile_options_for_single_package( config, - CompileMode::Doc { deps: false }, + CompileMode::Doc { + dep_mode: DepDocMode::NoDeps, + }, Some(&ws), )?; let target_args = values(args, "args"); diff --git a/src/cargo/core/compiler/build_config.rs b/src/cargo/core/compiler/build_config.rs index f5fbe119354..84629c03265 100644 --- a/src/cargo/core/compiler/build_config.rs +++ b/src/cargo/core/compiler/build_config.rs @@ -148,14 +148,24 @@ pub enum CompileMode { /// allows some de-duping of Units to occur. Bench, /// A target that will be documented with `rustdoc`. - /// If `deps` is true, then it will also document all dependencies. - Doc { deps: bool }, + /// `dep_mode` determines what set of packages will be documented. + Doc { dep_mode: DepDocMode }, /// A target that will be tested with `rustdoc`. Doctest, /// A marker for Units that represent the execution of a `build.rs` script. RunCustomBuild, } +/// Specific mode for rustdoc to use when documenting dependencies +#[derive(Clone, Copy, PartialEq, Debug, Eq, Hash, PartialOrd, Ord)] +pub enum DepDocMode { + Normal, + Development, + Build, + NoDeps, + All, +} + impl ser::Serialize for CompileMode { fn serialize(&self, s: S) -> Result where @@ -216,14 +226,27 @@ impl CompileMode { /// List of all modes (currently used by `cargo clean -p` for computing /// all possible outputs). pub fn all_modes() -> &'static [CompileMode] { - static ALL: [CompileMode; 9] = [ + static ALL: [CompileMode; 12] = [ CompileMode::Test, CompileMode::Build, CompileMode::Check { test: true }, CompileMode::Check { test: false }, CompileMode::Bench, - CompileMode::Doc { deps: true }, - CompileMode::Doc { deps: false }, + CompileMode::Doc { + dep_mode: DepDocMode::Build, + }, + CompileMode::Doc { + dep_mode: DepDocMode::All, + }, + CompileMode::Doc { + dep_mode: DepDocMode::NoDeps, + }, + CompileMode::Doc { + dep_mode: DepDocMode::Normal, + }, + CompileMode::Doc { + dep_mode: DepDocMode::Development, + }, CompileMode::Doctest, CompileMode::RunCustomBuild, ]; diff --git a/src/cargo/core/compiler/context/unit_dependencies.rs b/src/cargo/core/compiler/context/unit_dependencies.rs index db0744476c7..887116ef3e4 100644 --- a/src/cargo/core/compiler/context/unit_dependencies.rs +++ b/src/cargo/core/compiler/context/unit_dependencies.rs @@ -16,7 +16,7 @@ //! graph of `Unit`s, which capture these properties. use crate::core::compiler::Unit; -use crate::core::compiler::{BuildContext, CompileMode, Context, Kind}; +use crate::core::compiler::{BuildContext, CompileMode, Context, DepDocMode, Kind}; use crate::core::dependency::Kind as DepKind; use crate::core::package::Downloads; use crate::core::profiles::UnitFor; @@ -293,12 +293,26 @@ fn compute_deps_doc<'a, 'cfg, 'tmp>( state: &mut State<'a, 'cfg, 'tmp>, ) -> CargoResult, UnitFor)>> { let bcx = state.cx.bcx; + + let dep_mode = match bcx.build_config.mode { + CompileMode::Doc { dep_mode } => dep_mode, + _ => unreachable!(), + }; + let deps = bcx .resolve .deps(unit.pkg.package_id()) .filter(|&(_id, deps)| { deps.iter().any(|dep| match dep.kind() { DepKind::Normal => bcx.dep_platform_activated(dep, unit.kind), + DepKind::Development + if dep_mode == DepDocMode::Development || dep_mode == DepDocMode::All => + { + bcx.dep_platform_activated(dep, unit.kind) + } + DepKind::Build if dep_mode == DepDocMode::Build || dep_mode == DepDocMode::All => { + bcx.dep_platform_activated(dep, unit.kind) + } _ => false, }) }); @@ -322,7 +336,10 @@ fn compute_deps_doc<'a, 'cfg, 'tmp>( let dep_unit_for = UnitFor::new_normal().with_for_host(lib.for_host()); let lib_unit = new_unit(bcx, dep, lib, dep_unit_for, unit.kind.for_target(lib), mode); ret.push((lib_unit, dep_unit_for)); - if let CompileMode::Doc { deps: true } = unit.mode { + if (CompileMode::Doc { + dep_mode: DepDocMode::NoDeps, + }) != unit.mode + { // Document this lib as well. let doc_unit = new_unit( bcx, diff --git a/src/cargo/core/compiler/mod.rs b/src/cargo/core/compiler/mod.rs index 628ac8bbff8..9e8e6afa392 100644 --- a/src/cargo/core/compiler/mod.rs +++ b/src/cargo/core/compiler/mod.rs @@ -24,7 +24,7 @@ use log::debug; use same_file::is_same_file; use serde::Serialize; -pub use self::build_config::{BuildConfig, CompileMode, MessageFormat}; +pub use self::build_config::{BuildConfig, CompileMode, DepDocMode, MessageFormat}; pub use self::build_context::{BuildContext, FileFlavor, TargetConfig, TargetInfo}; use self::build_plan::BuildPlan; pub use self::compilation::{Compilation, Doctest}; diff --git a/src/cargo/util/command_prelude.rs b/src/cargo/util/command_prelude.rs index b8f208ea3e3..511ecf00857 100644 --- a/src/cargo/util/command_prelude.rs +++ b/src/cargo/util/command_prelude.rs @@ -15,7 +15,7 @@ use crate::util::{ use crate::CargoResult; use clap::{self, SubCommand}; -pub use crate::core::compiler::CompileMode; +pub use crate::core::compiler::{CompileMode, DepDocMode}; pub use crate::{CliError, CliResult, Config}; pub use clap::{AppSettings, Arg, ArgMatches};