pub trait PullRequestActions {
fn pr_body_or_die(pr_num: u32) -> String;
fn pr_head_ref_or_die(pr_num: u32) -> String;
fn pr_base_ref(pr_num: u32) -> Option<String>;
fn pr_review_decision(pr_num: u32) -> Option<String>;
fn pr_auto_merge_status_raw(pr_num: u32) -> Option<String>;
fn pr_is_auto_merge_enabled(pr_num: u32) -> bool;
fn pr_comment_bodies(pr_num: u32) -> Option<String>;
fn pr_diff_or_die(pr_num: u32) -> String;
fn pr_comments(pr_num: u32) -> Option<PrComments>;
fn pr_conflict_view(pr_num: u32) -> Option<PrConflictView>;
fn pr_diagnostic(pr_num: u32) -> Option<PrDiagnostic>;
fn pr_status_refresh(pr_num: u32) -> Option<PrStatusRefresh>;
fn pr_reviews(pr_num: u32) -> Option<Vec<PrReviewSummaryRecord>>;
fn current_branch_pr_summary() -> Option<CurrentBranchPrSummary>;
fn find_open_pr_url_for_head(branch: &str) -> (bool, String);
fn find_open_pr_head_for_head(branch: &str) -> Option<String>;
fn find_open_pr_number_for_head(branch: &str) -> Option<u32>;
fn open_pr_summaries(limit: u32) -> Option<Vec<cli_common::PrSummary>>;
fn merged_pr_summaries(limit: u32) -> Option<Vec<MergedPrSummary>>;
fn open_merge_candidate_prs_or_die(context: &str) -> Vec<OpenMergeCandidatePr>;
fn try_open_merge_candidate_prs() -> Option<Vec<OpenMergeCandidatePr>>;
fn create_pr(head: &str, base: &str, title: &str, body: &str) -> bool;
fn update_pr_branch(pr_num: u32) -> bool;
fn update_pr_branch_capture(pr_num: u32) -> (bool, String);
fn edit_pr_base(pr_num: u32, new_base: &str) -> bool;
fn merge_pr_squash(pr_num: u32) -> (bool, String);
fn enable_pr_auto_merge_squash(pr_num: u32) -> (bool, String);
fn comment_on_pr(pr_num: u32, body: &str) -> (bool, String);
fn submit_pr_review_with_env(
pr_num: u32,
action: &str,
body: &str,
env: &[(String, String)],
) -> bool;
fn mark_review_thread_resolved(thread_id: &str) -> Option<String>;
fn fetch_pr_review_threads(pr_num: u32) -> Option<Vec<PrReviewThread>>;
fn fetch_open_pr_review_threads_batched() -> Option<Vec<OpenPrReviewThreads>>;
}
pub trait IssueActions {
fn issue_body_or_die(issue_num: u32, context: &str) -> String;
fn issue_title_or_die(issue_num: u32, context: &str) -> String;
fn edit_issue_body(issue_num: u32, body: &str) -> bool;
fn close_issue(issue_num: u32) -> bool;
fn open_issue_summaries_with_label(label: &str) -> Option<Vec<IssueSummary>>;
fn open_issue_summaries(limit: u32) -> Option<Vec<OpenIssueSummary>>;
fn open_issue_housekeeping(limit: u32) -> Option<Vec<OpenIssueHousekeeping>>;
fn closed_issue_summaries(limit: u32) -> Option<Vec<ClosedIssueSummary>>;
fn open_issue_numbers_matching_title(search: &str) -> Option<String>;
fn first_open_issue_body_for_label(label: &str) -> String;
}
pub trait RepoActions {
fn repo_name_with_owner() -> Option<String>;
}
pub trait DeveloperPlatform: PullRequestActions + IssueActions + RepoActions {}
use serde::{Deserialize, Serialize};
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub enum IntegrationReadiness {
Clean,
Behind,
Dirty,
Blocked,
Unstable,
HasHooks,
Draft,
Unknown(String),
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub enum ApprovalGate {
Approved,
ChangesRequested,
ReviewRequired,
None,
Unknown(String),
}
#[derive(Clone, Debug, Default, PartialEq, Eq, Serialize, Deserialize)]
pub struct PlatformCheckStatus {
pub typename: Option<String>,
pub name: Option<String>,
pub context: Option<String>,
pub state: Option<String>,
pub conclusion: Option<String>,
pub status: Option<String>,
pub target_url: Option<String>,
pub details_url: Option<String>,
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub struct PrCommentRecord {
pub body: String,
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub struct PrComments {
pub comments: Vec<PrCommentRecord>,
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub struct PrConflictView {
pub head_ref: String,
pub base_ref: String,
pub integration_readiness: Option<IntegrationReadiness>,
pub title: String,
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub struct PrDiagnostic {
pub number: u32,
pub title: String,
pub head_ref: String,
pub base_ref: String,
pub is_draft: bool,
pub integration_readiness: Option<IntegrationReadiness>,
pub approval_gate: Option<ApprovalGate>,
pub status_check_rollup: Vec<PlatformCheckStatus>,
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub struct PrStatusRefresh {
pub integration_readiness: Option<IntegrationReadiness>,
pub approval_gate: Option<ApprovalGate>,
pub is_draft: bool,
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub struct PrReviewSummaryRecord {
pub author_login: String,
pub state: String,
pub submitted_at: String,
pub body: String,
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub struct CurrentBranchPrSummary {
pub number: u32,
pub title: String,
pub head_ref: String,
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub struct MergedPrSummary {
pub number: u32,
pub title: String,
pub merged_at: String,
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub struct OpenMergeCandidatePr {
pub number: u32,
pub head_ref: String,
pub base_ref: String,
pub is_draft: bool,
pub integration_readiness: Option<IntegrationReadiness>,
pub approval_gate: Option<ApprovalGate>,
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub struct PrReviewThreadComment {
pub author_login: String,
pub author_type: Option<String>,
pub path: Option<String>,
pub line: Option<u32>,
pub original_line: Option<u32>,
pub body: String,
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub struct PrReviewThread {
pub id: String,
pub is_resolved: bool,
pub comments: Vec<PrReviewThreadComment>,
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub struct OpenPrReviewThreads {
pub pr_number: u32,
pub review_threads: Vec<PrReviewThread>,
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub struct IssueSummary {
pub number: u32,
pub title: String,
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub struct IssueLabel {
pub name: String,
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub struct IssueAssignee {
pub login: String,
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub struct OpenIssueSummary {
pub number: u32,
pub title: String,
pub labels: Vec<IssueLabel>,
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub struct OpenIssueHousekeeping {
pub number: u32,
pub title: String,
pub labels: Vec<IssueLabel>,
pub updated_at: String,
pub assignees: Vec<IssueAssignee>,
}
#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)]
pub struct ClosedIssueSummary {
pub number: u32,
pub title: String,
pub closed_at: String,
}
pub fn map_integration_readiness(raw: &str) -> IntegrationReadiness {
match raw.trim().to_ascii_uppercase().as_str() {
"CLEAN" => IntegrationReadiness::Clean,
"BEHIND" => IntegrationReadiness::Behind,
"DIRTY" => IntegrationReadiness::Dirty,
"BLOCKED" => IntegrationReadiness::Blocked,
"UNSTABLE" => IntegrationReadiness::Unstable,
"HAS_HOOKS" => IntegrationReadiness::HasHooks,
"DRAFT" => IntegrationReadiness::Draft,
other => IntegrationReadiness::Unknown(other.to_string()),
}
}
pub fn map_approval_gate(raw: &str) -> ApprovalGate {
match raw.trim().to_ascii_uppercase().as_str() {
"APPROVED" => ApprovalGate::Approved,
"CHANGES_REQUESTED" => ApprovalGate::ChangesRequested,
"REVIEW_REQUIRED" => ApprovalGate::ReviewRequired,
"" => ApprovalGate::None,
other => ApprovalGate::Unknown(other.to_string()),
}
}