Last active
March 30, 2022 08:56
-
-
Save bluzky/380995c41cd205170b7193b50d87f9c7 to your computer and use it in GitHub Desktop.
Export your github pull request with Elixir
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Mix.install([ | |
{:tesla, "~> 1.4.3"}, | |
{:csv, "~> 2.4"}, | |
{:jason, "~> 1.3"} | |
]) | |
defmodule GithubPR do | |
require Logger | |
def exec(repo, token) do | |
headers = [ | |
:id, | |
:title, | |
:url, | |
:state, | |
:ticket, | |
:user, | |
:reviewer, | |
:created_at, | |
:updated_at, | |
:merged_at | |
] | |
stream_pr(repo, token) | |
|> CSV.encode(headers: headers) | |
|> Stream.into(File.stream!("pullrequest.csv", [:write, :utf8])) | |
|> Stream.run() | |
end | |
defp stream_pr(repo, token) do | |
per_page = 30 | |
# update your filters | |
params = %{per_page: 30, state: "closed"} | |
Stream.resource( | |
fn -> %{page: 1} end, | |
fn | |
%{page: page} -> | |
params = Map.put(params, :page, page) | |
prs = | |
Tesla.get("https://api.github.com/repos/#{repo}/pulls", | |
query: params, | |
headers: [ | |
{"Authorization", "token #{token}"}, | |
{"Content-Type", "application/json; charset=utf-8"}, | |
{"User-Agent", "Awesome-Octocat-App"} | |
] | |
) | |
|> parse_response() | |
|> Enum.map(&load_reviewer(&1, repo, token)) | |
if prs == [] do | |
{:halt, nil} | |
else | |
{prs, %{page: page + 1}} | |
end | |
_ -> | |
{:halt, nil} | |
end, | |
fn _ -> nil end | |
) | |
end | |
defp parse_response(response) do | |
case response do | |
{:ok, %{body: body, status: status}} when status >= 200 and status < 300 -> | |
body | |
|> Jason.decode!() | |
|> Enum.map(&parse_pr/1) | |
_ -> | |
Logger.error(inspect(response)) | |
end | |
end | |
defp parse_pr(item) do | |
%{ | |
id: item["number"], | |
number: item["number"], | |
url: item["url"], | |
state: item["state"], | |
title: item["title"], | |
ticket: ticket_number(item["title"]) || ticket_number(item["head"]["label"]), | |
user: item["user"]["login"], | |
reviewer: Enum.map(item["requested_reviewers"], & &1["login"]) |> Enum.join(","), | |
created_at: item["created_at"], | |
updated_at: item["created_at"], | |
merged_at: item["merged_at"] | |
} | |
end | |
defp ticket_number(string) do | |
case Regex.run(~r/.*(os[\-\s]\d+|cu[\-\s][a-z0-9]+).*/, string) do | |
[_, match] -> match | |
_ -> nil | |
end | |
end | |
defp load_reviewer(pr, repo, token) do | |
response = | |
Tesla.get("https://api.github.com/repos/#{repo}/pulls/#{pr.number}/reviews", | |
headers: [ | |
{"Authorization", "token #{token}"}, | |
{"Content-Type", "application/json; charset=utf-8"}, | |
{"User-Agent", "Awesome-Octocat-App"} | |
] | |
) | |
case response do | |
{:ok, %{body: body, status: status}} when status >= 200 and status < 300 -> | |
reviewers = | |
body | |
|> Jason.decode!() | |
|> Enum.map(& &1["user"]["login"]) | |
|> Enum.uniq() | |
|> Enum.join(",") | |
%{pr | reviewer: reviewers} | |
_ -> | |
pr | |
end | |
end | |
end | |
GithubPR.exec("bluzky/tarams", "your_token") |
Amazing script 💯
Its save for me thousand hours
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Create your access token here https://github.com/settings/tokens
remember to check
repo
checkbox