Skip to main content

git_stk/commands/
credits.rs

1use anyhow::Result;
2
3use crate::commands::Run;
4use crate::style;
5
6/// The tools that charted stacked work before git-stk, each with the homepage
7/// or repo to go read for yourself. Ordered loosely by how directly they shaped
8/// the workflow here.
9const INSPIRATIONS: &[(&str, &str, &str)] = &[
10    (
11        "Graphite",
12        "A faster, more intuitive Git interface",
13        "https://graphite.dev",
14    ),
15    (
16        "spr",
17        "Stacked Pull Requests on GitHub",
18        "https://github.com/ejoffe/spr",
19    ),
20    (
21        "ghstack",
22        "Submit stacked diffs to GitHub on the command line",
23        "https://github.com/ezyang/ghstack",
24    ),
25    (
26        "git-branchless",
27        "High-velocity, monorepo-scale workflow for Git",
28        "https://github.com/arxanas/git-branchless",
29    ),
30    (
31        "git-town",
32        "Git branches made easy",
33        "https://www.git-town.com",
34    ),
35    (
36        "Sapling",
37        "A Scalable, User-Friendly Source Control System",
38        "https://sapling-scm.com",
39    ),
40    (
41        "Jujutsu (jj)",
42        "A Git-compatible VCS that is both simple and powerful",
43        "https://github.com/jj-vcs/jj",
44    ),
45];
46
47/// Show attribution for the tools that inspired git-stk.
48#[derive(Debug, clap::Args)]
49pub struct Credits;
50
51impl Run for Credits {
52    fn run(self) -> Result<()> {
53        // Pad names to the widest so the blurbs line up in a column.
54        let width = INSPIRATIONS
55            .iter()
56            .map(|(name, _, _)| name.chars().count())
57            .max()
58            .unwrap_or(0);
59
60        anstream::println!(
61            "git-stk could not have been made without the tools that explored stacked branch workflows before it:\n"
62        );
63        for (name, blurb, url) in INSPIRATIONS {
64            // Pad the plain name to the column width, then paint just the name,
65            // so the ANSI codes never throw off the alignment.
66            let pad = " ".repeat(width - name.chars().count());
67            anstream::println!("  {}{pad}  {blurb}", style::paint(style::BRANCH, name));
68            // The URL sits indented under its blurb.
69            let indent = " ".repeat(width + 2);
70            anstream::println!("  {indent}{}", style::paint(style::DIM, url));
71        }
72        anstream::println!("{}", style::paint(style::DIM, "\nBuilt by Lara Kelley (@lararosekelley)"));
73        Ok(())
74    }
75}