Skip to content

Commit 36ec7e4

Browse files
authored
Merge pull request #521 from Kobzol/rollup-duplicate
Filter out duplicate PRs when making a rollup
2 parents 64f5661 + 00d1aa8 commit 36ec7e4

File tree

1 file changed

+34
-5
lines changed

1 file changed

+34
-5
lines changed

src/github/rollup.rs

Lines changed: 34 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ use axum::http::StatusCode;
1010
use axum::response::{IntoResponse, Redirect, Response};
1111
use futures::StreamExt;
1212
use rand::{Rng, distr::Alphanumeric};
13+
use std::collections::HashSet;
1314
use std::sync::Arc;
1415
use tracing::Instrument;
1516

@@ -151,16 +152,23 @@ async fn create_rollup(
151152
let OAuthRollupState {
152153
repo_name,
153154
repo_owner,
154-
pr_nums,
155+
mut pr_nums,
155156
} = rollup_state;
156157

157158
let username = user_client.username;
158159

159160
tracing::info!("User {username} is creating a rollup with PRs: {pr_nums:?}");
160161

162+
// Filter out duplicates
163+
let mut pr_set = HashSet::new();
164+
pr_nums.retain(|&pr| pr_set.insert(pr));
165+
161166
if pr_nums.len() as u64 > ROLLUP_PR_LIMIT {
162167
return Err(RollupError::TooManyPullRequests);
163168
}
169+
if pr_nums.is_empty() {
170+
return Err(RollupError::NoPullRequestsSelected);
171+
}
164172

165173
// Ensure user has a fork
166174
match user_client.client.get_repo().await {
@@ -198,10 +206,6 @@ async fn create_rollup(
198206
}
199207
}
200208

201-
if rollup_prs.is_empty() {
202-
return Err(RollupError::NoPullRequestsSelected);
203-
}
204-
205209
// Sort PRs by priority and then PR number
206210
// We want to try to merge PRs with higher priority first, so that in case of conflicts they
207211
// get in, rather than being left out.
@@ -553,6 +557,31 @@ mod tests {
553557
");
554558
}
555559

560+
#[sqlx::test]
561+
async fn rollup_duplicates(pool: sqlx::PgPool) {
562+
let gh = run_test((pool, rollup_state()), async |ctx: &mut BorsTester| {
563+
let pr2 = ctx.open_pr(default_repo_name(), |_| {}).await?;
564+
let pr3 = ctx.open_pr(default_repo_name(), |_| {}).await?;
565+
ctx.approve(pr2.id()).await?;
566+
ctx.approve(pr3.id()).await?;
567+
568+
make_rollup(ctx, &[&pr3, &pr2, &pr3, &pr2])
569+
.await?
570+
.assert_status(StatusCode::TEMPORARY_REDIRECT);
571+
Ok(())
572+
})
573+
.await;
574+
let repo = gh.get_repo(());
575+
insta::assert_snapshot!(repo.lock().get_pr(4).description, @r"
576+
Successful merges:
577+
578+
- #2 (Title of PR 2)
579+
- #3 (Title of PR 3)
580+
581+
r? @ghost
582+
");
583+
}
584+
556585
async fn make_rollup(
557586
ctx: &mut BorsTester,
558587
prs: &[&PullRequest],

0 commit comments

Comments
 (0)