Skip to content
Open
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
57 changes: 56 additions & 1 deletion crates/gateway/src/webhook.rs
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,21 @@ pub fn verify_github_signature(secret: &str, body: &[u8], signature_header: &str
}

/// Returns attestation inputs when the payload is a merged PR on the default branch.

/// Map GitHub PR labels to Wave complexity points.
/// Labels follow Drips Wave convention: complexity:low=1, complexity:medium=3, complexity:high=5.
fn label_to_points(labels: &[waveflow_shared::GitHubLabel]) -> u32 {
for label in labels {
match label.name.as_str() {
"complexity:high" => return 5,
"complexity:medium" => return 3,
"complexity:low" => return 2,
_ => continue,
}
}
1 // default points when no recognized complexity label
}

pub fn parse_merge_event(payload: &GitHubPullRequestEvent) -> WaveFlowResult<MergeAttestation> {
if payload.action != "closed" {
return Err(WaveFlowError::Validation("ignored non-closed action".into()));
Expand All @@ -42,7 +57,7 @@ pub fn parse_merge_event(payload: &GitHubPullRequestEvent) -> WaveFlowResult<Mer
github_repo: payload.repository.full_name.clone(),
github_username: payload.pull_request.user.login.clone(),
pr_number: payload.number,
points: 1,
points: label_to_points(&payload.pull_request.labels),
})
}

Expand Down Expand Up @@ -71,6 +86,7 @@ mod tests {
base: GitHubRef {
ref_name: base_ref.into(),
},
labels: vec![],
},
repository: GitHubRepository {
full_name: "StellarRoute/WaveFlow".into(),
Expand Down Expand Up @@ -122,3 +138,42 @@ mod tests {
assert!(matches!(err, WaveFlowError::Validation(_)));
}
}


#[test]
fn parse_merge_event_maps_complexity_labels_to_points() {
let mut event = sample_event(true, "main", "main");
event.pull_request.labels = vec![
waveflow_shared::GitHubLabel { name: "complexity:medium".into() },
waveflow_shared::GitHubLabel { name: "bug".into() },
];
let attestation = parse_merge_event(&event).expect("merge");
assert_eq!(attestation.points, 3);
}

#[test]
fn parse_merge_event_defaults_points_to_1_without_label() {
let event = sample_event(true, "main", "main");
let attestation = parse_merge_event(&event).expect("merge");
assert_eq!(attestation.points, 1);
}

#[test]
fn parse_merge_event_maps_high_complexity() {
let mut event = sample_event(true, "main", "main");
event.pull_request.labels = vec![
waveflow_shared::GitHubLabel { name: "complexity:high".into() },
];
let attestation = parse_merge_event(&event).expect("merge");
assert_eq!(attestation.points, 5);
}

#[test]
fn parse_merge_event_maps_low_complexity() {
let mut event = sample_event(true, "main", "main");
event.pull_request.labels = vec![
waveflow_shared::GitHubLabel { name: "complexity:low".into() },
];
let attestation = parse_merge_event(&event).expect("merge");
assert_eq!(attestation.points, 2);
}
7 changes: 7 additions & 0 deletions crates/shared/src/types.rs
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,13 @@ pub struct GitHubPullRequest {
pub merged: bool,
pub user: GitHubUser,
pub base: GitHubRef,
#[serde(default)]
pub labels: Vec<GitHubLabel>,
}

#[derive(Debug, Clone, Deserialize, Serialize)]
pub struct GitHubLabel {
pub name: String,
}

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