Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions crates/nixpkgs-track/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ thiserror = "2.0.11"
env_logger = "0.11.6"
user_dirs = "0.2.0"
dialoguer = "0.11.0"
regex = "1.11.1"

[lints]
workspace = true
39 changes: 35 additions & 4 deletions crates/nixpkgs-track/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ use std::sync::Arc;
use clap::{Parser, Subcommand};
use dialoguer::MultiSelect;
use miette::{Context, IntoDiagnostic};
use regex::Regex;
use serde::{Deserialize, Serialize};

use chrono::Utc;
Expand All @@ -13,7 +14,8 @@ use yansi::hyperlink::HyperlinkExt;
use nixpkgs_track::utils::{format_seconds_to_time_ago, parse_pull_request_id};
use nixpkgs_track_lib::{branch_contains_commit, fetch_nixpkgs_pull_request, NixpkgsTrackError};

static DEFAULT_BRANCHES: [&str; 6] = ["master", "staging", "staging-next", "nixpkgs-unstable", "nixos-unstable-small", "nixos-unstable"];
static ROLLING_BRANCHES: [&str; 6] = ["staging", "staging-next", "master", "nixpkgs-unstable", "nixos-unstable-small", "nixos-unstable"];
static STABLE_BRANCHES_TEMPLATE: [&str; 6] = ["staging-XX.XX", "staging-next-XX.XX", "release-XX.XX", "nixpkgs-XX.XX-darwin", "nixos-XX.XX-small", "nixos-XX.XX"];

#[derive(Parser)]
#[command(version, about, subcommand_negates_reqs = true)]
Expand Down Expand Up @@ -93,11 +95,40 @@ async fn check(client: Arc<reqwest::Client>, pull_request: u64, token: Option<&s
.signed_duration_since(pull_request.created_at)
.num_seconds(),
);
let merged_into_branch = pull_request.base.r#ref;

writeln!(
output,
"Merged {merged_at_ago} ago ({merged_at_date}), {creation_to_merge_time} after creation, into branch '{merged_into_branch}'."
)?;

let stable_branches: Option<Vec<String>> = if ROLLING_BRANCHES.contains(&merged_into_branch.as_str()) {
None
} else {
// regex for stable version XX.XX
let stable_version_regex = Regex::new(r"[0-9]+\.[0-9]+$").unwrap();
if let Some(stable_version) = stable_version_regex.find(&merged_into_branch) {
let stable_branches = STABLE_BRANCHES_TEMPLATE
.iter()
.map(|s| s.replace("XX.XX", stable_version.as_str()))
.collect();
Some(stable_branches)
} else {
None
}
};

writeln!(output, "Merged {merged_at_ago} ago ({merged_at_date}), {creation_to_merge_time} after creation.")?;
#[allow(clippy::redundant_closure_for_method_calls)]
let tracked_branches = match stable_branches {
Some(ref stable_branches) => stable_branches
.iter()
.map(|s| s.as_str())
.collect(),
None => Vec::from(ROLLING_BRANCHES),
};

let mut branches = tokio::task::JoinSet::new();
for (i, branch) in DEFAULT_BRANCHES.iter().enumerate() {
for (i, branch) in tracked_branches.iter().enumerate() {
let token_clone = token.map(ToOwned::to_owned);
let branch_clone = (*branch).to_string();
let commit_sha_clone = commit_sha.clone();
Expand All @@ -114,7 +145,7 @@ async fn check(client: Arc<reqwest::Client>, pull_request: u64, token: Option<&s

for (i, result) in results {
let has_pull_request = result?;
writeln!(output, "{}: {}", DEFAULT_BRANCHES[i], if has_pull_request { "✅" } else { "🚫" })?;
writeln!(output, "{}: {}", tracked_branches[i], if has_pull_request { "✅" } else { "🚫" })?;
}
} else {
let created_at_ago = format_seconds_to_time_ago(
Expand Down
20 changes: 19 additions & 1 deletion crates/nixpkgs-track_lib/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,10 @@ pub async fn fetch_nixpkgs_pull_request(client: impl AsRef<reqwest::Client>, pul
}

pub async fn branch_contains_commit(client: impl AsRef<reqwest::Client>, branch: &str, commit: &str, token: Option<&str>) -> Result<bool, NixpkgsTrackError> {
let url = format!("{BASE_API_URL}/compare/{branch}...{commit}");
// `per_page=1000000&page=100`: a hack for the API, to _not_ return
// information about files or commits, which we do not need here;
// we only need to know whether it's `ahead` or `behind`
let url = format!("{BASE_API_URL}/compare/{branch}...{commit}?per_page=1000000&page=100");
let response = build_request(client, &url, token)
.send()
.await;
Expand All @@ -69,6 +72,7 @@ pub struct User {
pub url: String,
}

#[non_exhaustive]
#[derive(Clone, Debug, Deserialize)]
pub struct PullRequest {
pub html_url: String,
Expand All @@ -79,6 +83,20 @@ pub struct PullRequest {
pub merged_at: Option<DateTime<Utc>>,
pub merged: bool,
pub merge_commit_sha: Option<String>,
/// Base branch that the pull request is merged into
pub base: ForkBranch,
/// Head branch that the pull request is merged from
pub head: ForkBranch,
}

#[non_exhaustive]
#[derive(Clone, Debug, Deserialize)]
pub struct ForkBranch {
/// Fork and branch name in the format "owner:branch"
pub label: String,
/// Branch name in a given fork
pub r#ref: String,
pub sha: String,
}

#[derive(Clone, Debug, Deserialize)]
Expand Down
Loading