Skip to content

Commit

Permalink
Merge pull request #1115 from hannobraun/automation
Browse files Browse the repository at this point in the history
Expand release automation
  • Loading branch information
hannobraun authored Sep 20, 2022
2 parents 408e5fa + 54a0790 commit f12bc32
Show file tree
Hide file tree
Showing 6 changed files with 160 additions and 9 deletions.
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 tools/automator/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ chrono = "0.4.22"
map-macro = "0.2.4"
octocrab = "0.17.0"
semver = "1.0.14"
serde = "1.0.144"
serde_json = "1.0.85"
url = "2.3.0"

Expand Down
5 changes: 1 addition & 4 deletions tools/automator/src/args.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
#[derive(clap::Parser)]
pub enum Args {
CreateReleaseAnnouncement(CreateReleaseAnnouncement),
Announcement,
Sponsors,
}

Expand All @@ -9,6 +9,3 @@ impl Args {
<Self as clap::Parser>::parse()
}
}

#[derive(clap::Parser)]
pub struct CreateReleaseAnnouncement {}
1 change: 1 addition & 0 deletions tools/automator/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ mod announcement;
mod args;
mod pull_requests;
mod run;
mod sponsors;

#[tokio::main]
async fn main() -> anyhow::Result<()> {
Expand Down
15 changes: 10 additions & 5 deletions tools/automator/src/run.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,23 +3,28 @@ use std::env;
use anyhow::Context;
use octocrab::Octocrab;

use crate::{announcement::create_release_announcement, args::Args};
use crate::{
announcement::create_release_announcement, args::Args,
sponsors::query_sponsors,
};

pub async fn run() -> anyhow::Result<()> {
let token = env::var("GITHUB_TOKEN")
.context("Loading env variable `GITHUB_TOKEN`")?;
let octocrab = Octocrab::builder().personal_token(token).build()?;

match Args::parse() {
Args::CreateReleaseAnnouncement(_) => {
Args::Announcement => {
create_release_announcement(&octocrab)
.await
.context("Failed to create release announcement")?;
}
Args::Sponsors => {
let response: serde_json::Value =
octocrab.graphql("query { viewer { login }}").await?;
println!("{response}");
let sponsors = query_sponsors(&octocrab)
.await
.context("Failed to query sponsors")?;

println!("{sponsors:#?}");

todo!("Querying sponsors is not supported yet.")
}
Expand Down
146 changes: 146 additions & 0 deletions tools/automator/src/sponsors.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,146 @@
use std::cmp::Ordering;

use chrono::{DateTime, Utc};
use octocrab::Octocrab;

#[derive(Debug, Eq, PartialEq)]
pub struct Sponsor {
pub login: String,
pub since: DateTime<Utc>,
pub dollars: u32,
}

impl Ord for Sponsor {
fn cmp(&self, other: &Self) -> Ordering {
let by_dollars = other.dollars.cmp(&self.dollars);
let by_date = self.since.cmp(&other.since);
let by_login = self.login.cmp(&other.login);

if by_dollars.is_ne() {
return by_dollars;
}

if by_date.is_ne() {
return by_date;
}

by_login
}
}

impl PartialOrd for Sponsor {
fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
Some(self.cmp(other))
}
}

pub async fn query_sponsors(
octocrab: &Octocrab,
) -> anyhow::Result<Vec<Sponsor>> {
let response: QueryResult = octocrab
.graphql(
"query {
viewer {
sponsors(first: 100) {
nodes {
__typename
... on User {
login
sponsorshipForViewerAsSponsorable {
createdAt
tier {
monthlyPriceInDollars
}
}
}
... on Organization {
login
sponsorshipForViewerAsSponsorable {
createdAt
tier {
monthlyPriceInDollars
}
}
}
}
}
}
}",
)
.await?;

let mut sponsors = response
.data
.viewer
.sponsors
.nodes
.into_iter()
.map(|node| {
let login = node.login;
let since = node.sponsorship_for_viewer_as_sponsorable.created_at;
let dollars = node
.sponsorship_for_viewer_as_sponsorable
.tier
.monthly_price_in_dollars;

Sponsor {
login,
since,
dollars,
}
})
.collect::<Vec<_>>();

if sponsors.len() >= 100 {
todo!(
"Number of sponsors has reached max page size, but query does not \
support pagination."
)
}

sponsors.sort();

Ok(sponsors)
}

#[derive(Debug, serde::Deserialize)]
pub struct QueryResult {
pub data: QueryResultData,
}

#[derive(Debug, serde::Deserialize)]
pub struct QueryResultData {
pub viewer: QueryResultViewer,
}

#[derive(Debug, serde::Deserialize)]
pub struct QueryResultViewer {
pub sponsors: QueryResultSponsorsNodes,
}

#[derive(Debug, serde::Deserialize)]
pub struct QueryResultSponsorsNodes {
pub nodes: Vec<QueryResultSponsorsNode>,
}

#[derive(Debug, serde::Deserialize)]
pub struct QueryResultSponsorsNode {
pub login: String,

#[serde(rename = "sponsorshipForViewerAsSponsorable")]
pub sponsorship_for_viewer_as_sponsorable: QueryResultSponsorable,
}

#[derive(Debug, serde::Deserialize)]
pub struct QueryResultSponsorable {
#[serde(rename = "createdAt")]
pub created_at: DateTime<Utc>,

pub tier: QueryResultSponsorableTier,
}

#[derive(Debug, serde::Deserialize)]
pub struct QueryResultSponsorableTier {
#[serde(rename = "monthlyPriceInDollars")]
pub monthly_price_in_dollars: u32,
}

0 comments on commit f12bc32

Please sign in to comment.