1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
mod ci;
mod fixup;
mod kotlin;
mod release;
mod swift;
mod workspace;

use ci::CiArgs;
use clap::{Parser, Subcommand};
use fixup::FixupArgs;
use kotlin::KotlinArgs;
use release::ReleaseArgs;
use swift::SwiftArgs;
use xshell::cmd;

const NIGHTLY: &str = "nightly-2024-06-25";

type Result<T, E = Box<dyn std::error::Error>> = std::result::Result<T, E>;

#[derive(Parser)]
struct Xtask {
    #[clap(subcommand)]
    cmd: Command,
}

#[derive(Subcommand)]
enum Command {
    /// Run continuous integration checks
    Ci(CiArgs),
    /// Fix up automatic checks
    Fixup(FixupArgs),
    /// Build the SDKs documentation
    Doc {
        /// Opens the docs in a browser after the operation
        #[clap(long)]
        open: bool,
    },
    /// Prepare and publish a release of the matrix-sdk crates
    Release(ReleaseArgs),
    Swift(SwiftArgs),
    Kotlin(KotlinArgs),
}

fn main() -> Result<()> {
    match Xtask::parse().cmd {
        Command::Ci(ci) => ci.run(),
        Command::Fixup(cfg) => cfg.run(),
        Command::Doc { open } => build_docs(open.then_some("--open"), DenyWarnings::No),
        Command::Swift(cfg) => cfg.run(),
        Command::Kotlin(cfg) => cfg.run(),
        Command::Release(cfg) => cfg.run(),
    }
}

enum DenyWarnings {
    Yes,
    No,
}

fn build_docs(
    extra_args: impl IntoIterator<Item = &'static str>,
    deny_warnings: DenyWarnings,
) -> Result<()> {
    let mut rustdocflags = "--enable-index-page -Zunstable-options --cfg docsrs".to_owned();
    if let DenyWarnings::Yes = deny_warnings {
        rustdocflags += " -Dwarnings";
    }

    // Keep in sync with .github/workflows/docs.yml
    cmd!("rustup run {NIGHTLY} cargo doc --no-deps --workspace --features docsrs")
        .env("RUSTDOCFLAGS", rustdocflags)
        .args(extra_args)
        .run()?;

    Ok(())
}