|
7 | 7 | //! Everything here is basically just a shim around calling either `rustbook` or
|
8 | 8 | //! `rustdoc`.
|
9 | 9 |
|
10 |
| -use std::fs; |
| 10 | +use std::io::{self, Write}; |
11 | 11 | use std::path::{Path, PathBuf};
|
| 12 | +use std::{fs, mem}; |
12 | 13 |
|
13 | 14 | use crate::core::build_steps::compile;
|
14 | 15 | use crate::core::build_steps::tool::{self, prepare_tool_cargo, SourceType, Tool};
|
@@ -388,6 +389,104 @@ impl Step for Standalone {
|
388 | 389 | }
|
389 | 390 | }
|
390 | 391 |
|
| 392 | +#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)] |
| 393 | +pub struct Releases { |
| 394 | + compiler: Compiler, |
| 395 | + target: TargetSelection, |
| 396 | +} |
| 397 | + |
| 398 | +impl Step for Releases { |
| 399 | + type Output = (); |
| 400 | + const DEFAULT: bool = true; |
| 401 | + |
| 402 | + fn should_run(run: ShouldRun<'_>) -> ShouldRun<'_> { |
| 403 | + let builder = run.builder; |
| 404 | + run.path("RELEASES.md").alias("releases").default_condition(builder.config.docs) |
| 405 | + } |
| 406 | + |
| 407 | + fn make_run(run: RunConfig<'_>) { |
| 408 | + run.builder.ensure(Releases { |
| 409 | + compiler: run.builder.compiler(run.builder.top_stage, run.builder.config.build), |
| 410 | + target: run.target, |
| 411 | + }); |
| 412 | + } |
| 413 | + |
| 414 | + /// Generates HTML release notes to include in the final docs bundle. |
| 415 | + /// |
| 416 | + /// This uses the same stylesheet and other tools as Standalone, but the |
| 417 | + /// RELEASES.md file is included at the root of the repository and gets |
| 418 | + /// the headline added. In the end, the conversion is done by Rustdoc. |
| 419 | + fn run(self, builder: &Builder<'_>) { |
| 420 | + let target = self.target; |
| 421 | + let compiler = self.compiler; |
| 422 | + let _guard = builder.msg_doc(compiler, "releases", target); |
| 423 | + let out = builder.doc_out(target); |
| 424 | + t!(fs::create_dir_all(&out)); |
| 425 | + |
| 426 | + builder.ensure(Standalone { |
| 427 | + compiler: builder.compiler(builder.top_stage, builder.config.build), |
| 428 | + target, |
| 429 | + }); |
| 430 | + |
| 431 | + let version_info = builder.ensure(SharedAssets { target: self.target }).version_info; |
| 432 | + |
| 433 | + let favicon = builder.src.join("src/doc/favicon.inc"); |
| 434 | + let footer = builder.src.join("src/doc/footer.inc"); |
| 435 | + let full_toc = builder.src.join("src/doc/full-toc.inc"); |
| 436 | + |
| 437 | + let html = out.join("releases.html"); |
| 438 | + let tmppath = out.join("releases.md"); |
| 439 | + let inpath = builder.src.join("RELEASES.md"); |
| 440 | + let rustdoc = builder.rustdoc(compiler); |
| 441 | + if !up_to_date(&inpath, &html) |
| 442 | + || !up_to_date(&footer, &html) |
| 443 | + || !up_to_date(&favicon, &html) |
| 444 | + || !up_to_date(&full_toc, &html) |
| 445 | + || !(builder.config.dry_run() |
| 446 | + || up_to_date(&version_info, &html) |
| 447 | + || up_to_date(&rustdoc, &html)) |
| 448 | + { |
| 449 | + let mut tmpfile = t!(fs::File::create(&tmppath)); |
| 450 | + t!(tmpfile.write_all(b"% Rust Release Notes\n\n")); |
| 451 | + t!(io::copy(&mut t!(fs::File::open(&inpath)), &mut tmpfile)); |
| 452 | + mem::drop(tmpfile); |
| 453 | + let mut cmd = builder.rustdoc_cmd(compiler); |
| 454 | + |
| 455 | + // Needed for --index-page flag |
| 456 | + cmd.arg("-Z").arg("unstable-options"); |
| 457 | + |
| 458 | + cmd.arg("--html-after-content") |
| 459 | + .arg(&footer) |
| 460 | + .arg("--html-before-content") |
| 461 | + .arg(&version_info) |
| 462 | + .arg("--html-in-header") |
| 463 | + .arg(&favicon) |
| 464 | + .arg("--markdown-no-toc") |
| 465 | + .arg("--markdown-css") |
| 466 | + .arg("rust.css") |
| 467 | + .arg("--index-page") |
| 468 | + .arg(&builder.src.join("src/doc/index.md")) |
| 469 | + .arg("--markdown-playground-url") |
| 470 | + .arg("https://play.rust-lang.org/") |
| 471 | + .arg("-o") |
| 472 | + .arg(&out) |
| 473 | + .arg(&tmppath); |
| 474 | + |
| 475 | + if !builder.config.docs_minification { |
| 476 | + cmd.arg("--disable-minification"); |
| 477 | + } |
| 478 | + |
| 479 | + builder.run(&mut cmd); |
| 480 | + } |
| 481 | + |
| 482 | + // We open doc/RELEASES.html as the default if invoked as `x.py doc --open RELEASES.md` |
| 483 | + // with no particular explicit doc requested (e.g. library/core). |
| 484 | + if builder.was_invoked_explicitly::<Self>(Kind::Doc) { |
| 485 | + builder.open_in_browser(&html); |
| 486 | + } |
| 487 | + } |
| 488 | +} |
| 489 | + |
391 | 490 | #[derive(Debug, Clone)]
|
392 | 491 | pub struct SharedAssetsPaths {
|
393 | 492 | pub version_info: PathBuf,
|
|
0 commit comments