use chrono::{DateTime, Utc};
use serde::{Deserialize, Serialize};
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "camelCase")]
pub struct DiffStats {
pub files_changed: i32,
pub insertions: i32,
pub deletions: i32,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "camelCase")]
pub struct PullRequest {
pub pr_id: String,
pub repo_id: String,
pub author_id: String,
pub source_branch: String,
pub target_branch: String,
pub title: String,
pub description: Option<String>,
pub status: String,
pub ci_status: String,
pub diff_stats: DiffStats,
pub mergeable: bool,
pub is_approved: bool,
pub review_count: i32,
pub created_at: DateTime<Utc>,
pub merged_at: Option<DateTime<Utc>>,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "camelCase")]
pub struct Review {
pub review_id: String,
pub pr_id: String,
pub reviewer_id: String,
pub verdict: String,
pub body: Option<String>,
pub created_at: DateTime<Utc>,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "camelCase")]
pub struct MergeResult {
pub pr_id: String,
pub repo_id: String,
pub merge_strategy: String,
pub merged_at: DateTime<Utc>,
pub merge_commit_oid: String,
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn test_pull_request_deserialize() {
let json = r#"{
"prId": "pr-123",
"repoId": "repo-456",
"authorId": "agent-789",
"sourceBranch": "feature/test",
"targetBranch": "main",
"title": "Add new feature",
"description": "This PR adds a new feature",
"status": "open",
"ciStatus": "passed",
"diffStats": {
"filesChanged": 5,
"insertions": 100,
"deletions": 20
},
"mergeable": true,
"isApproved": true,
"reviewCount": 2,
"createdAt": "2024-01-15T10:30:00Z",
"mergedAt": null
}"#;
let pr: PullRequest = serde_json::from_str(json).expect("Should deserialize");
assert_eq!(pr.pr_id, "pr-123");
assert_eq!(pr.status, "open");
assert!(pr.mergeable);
}
#[test]
fn test_review_verdicts() {
for verdict in ["approve", "request_changes", "comment"] {
let json = format!(
r#"{{
"reviewId": "review-123",
"prId": "pr-456",
"reviewerId": "agent-789",
"verdict": "{}",
"body": "LGTM",
"createdAt": "2024-01-15T10:30:00Z"
}}"#,
verdict
);
let review: Review = serde_json::from_str(&json).expect("Should deserialize");
assert_eq!(review.verdict, verdict);
}
}
}