ghamma 0.1.0 → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: a18af8838cf36204f7921d5342381a90d5af1de2df8e0132a2802774250a63ae
4
- data.tar.gz: 121780f2d92b3047915a97e8d132587ef72ccb42a87a5bde6ade7af2aa85fbb0
3
+ metadata.gz: 374a835681570e0824d2ee192361ed16dbfc11352cc8f8f0f69ad2a0cdaa8f7f
4
+ data.tar.gz: 702786830164573d586113f1f88b8c5e983e71111c9ce3226274e468a374fb61
5
5
  SHA512:
6
- metadata.gz: 1eebb5729dadc195e2d15d5e117a607228e650f0b20f50b161c037c9bf7b291c0dba50e4934785fc88f6445e9895fc08efc1f126f7993879d7f565cfc7ccf598
7
- data.tar.gz: cc6a75f3542ee2c81f6aa600b1361561867b802b64aa6794417ad122abc959971832de89662bfbeacc95d35b0e66111c2cf26a2f41c4988bd8faabd6ccd2070e
6
+ metadata.gz: 3e01904c7804ae9636d06aaad5af029736b8286200f2791851b10bdd11f6552721f7cdb2ab1c4dfe9489bd27ff98374f7d7037a15e0fb04ad22c396429b18361
7
+ data.tar.gz: f2fb982a98a100f66072fbc80d0c4618f1281de82442dcf59c2b551ade25466303684d7fcbf55cf56eefded0a4d43ad35ce95eb7148764e71b2dc840c08c9b51
data/CHANGELOG.md CHANGED
@@ -1,3 +1,15 @@
1
1
  ## [Unreleased]
2
2
 
3
- - Under development
3
+ -
4
+
5
+ ## [0.2.0] - 2023-06-01
6
+
7
+ - Breaking: Add commands to the CLI: `version`, `list-worklows`, `duration-history`
8
+
9
+ ## [0.1.1] - 2023-06-01
10
+
11
+ - Actually make the gem executable
12
+
13
+ ## [0.1.0] - 2023-06-01
14
+
15
+ - Initial gem bundling
data/Gemfile CHANGED
@@ -4,9 +4,3 @@ source "https://rubygems.org"
4
4
 
5
5
  # Specify your gem's dependencies in ghamma.gemspec
6
6
  gemspec
7
-
8
- gem "rake", "~> 13.0"
9
-
10
- gem "test-unit", "~> 3.0"
11
-
12
- gem "standard", "~> 1.3"
data/Gemfile.lock CHANGED
@@ -1,7 +1,8 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- ghamma (0.1.0)
4
+ ghamma (0.2.0)
5
+ dry-cli
5
6
  http
6
7
 
7
8
  GEM
@@ -12,6 +13,7 @@ GEM
12
13
  ast (2.4.2)
13
14
  domain_name (0.5.20190701)
14
15
  unf (>= 0.0.5, < 1.0.0)
16
+ dry-cli (1.0.0)
15
17
  ffi (1.15.5)
16
18
  ffi-compiler (1.0.1)
17
19
  ffi (>= 1.0.0)
@@ -75,12 +77,13 @@ GEM
75
77
 
76
78
  PLATFORMS
77
79
  arm64-darwin-22
80
+ x86_64-linux
78
81
 
79
82
  DEPENDENCIES
80
83
  ghamma!
81
- rake (~> 13.0)
82
- standard (~> 1.3)
83
- test-unit (~> 3.0)
84
+ rake
85
+ standard
86
+ test-unit
84
87
 
85
88
  BUNDLED WITH
86
89
  2.4.12
data/README.md CHANGED
@@ -13,17 +13,43 @@ If bundler is not being used to manage dependencies, install the gem by executin
13
13
 
14
14
  ## Usage
15
15
 
16
- TODO: Write usage instructions here
16
+ ### Authentication
17
+
18
+ The Github workflows API requires an authenticated user, even for public repos.
19
+ To use this tool, you will need a
20
+ [Github API Token](https://docs.github.com/en/rest/overview/authenticating-to-the-rest-api#authenticating-with-a-personal-access-token)
21
+ with at least `read` access to the repo you want to look at.
22
+
23
+ Once you have that, make it available.
24
+
25
+ ```
26
+ $ export GH_TOKEN="YOUR_API_TOKEN"
27
+ ```
28
+
29
+ Then fetch the list of available workflows for the repo. The name will be necessary in the next step.
30
+
31
+ ```
32
+ $ ghamma list-workflows tony-rowan ghamma
33
+ Found 1 workflows
34
+ Ruby
35
+ ```
36
+
37
+ Then fetch a CSV of the durations of the latest workflow runs.
38
+
39
+ ```
40
+ $ ghamma duration-history tony-rowan ghamma Ruby
41
+ Date,Duration
42
+ 2023-06-01T15:44:49Z,21000
43
+ 2023-06-01T15:37:21Z,17000
44
+ 2023-06-01T15:35:16Z,23000
45
+ 2023-06-01T15:31:33Z,19000
46
+ ```
17
47
 
18
48
  ## Development
19
49
 
20
50
  After checking out the repo, run `bin/setup` to install dependencies. Then, run `rake test-unit` to run the tests.
21
51
  You can also run `bin/console` for an interactive prompt that will allow you to experiment.
22
52
 
23
- To install this gem onto your local machine, run `bundle exec rake install`. To release a new version, update
24
- the version number in `version.rb`, and then run `bundle exec rake release`, which will create a git tag for the
25
- version, push git commits and the created tag, and push the `.gem` file to [rubygems.org](https://rubygems.org).
26
-
27
53
  ## Contributing
28
54
 
29
55
  Bug reports and pull requests are welcome on GitHub at https://github.com/tony-rowan/ghamma. This project is
data/exe/ghamma ADDED
@@ -0,0 +1,5 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require "ghamma"
4
+
5
+ Dry::CLI.new(Ghamma::CLI).call
data/lib/ghamma/cli.rb ADDED
@@ -0,0 +1,60 @@
1
+ require "csv"
2
+ require "dry/cli"
3
+ require "http"
4
+
5
+ require_relative "./github_api_client"
6
+ require_relative "./version"
7
+
8
+ module Ghamma
9
+ module CLI
10
+ extend Dry::CLI::Registry
11
+
12
+ class Version < Dry::CLI::Command
13
+ desc "Print version"
14
+
15
+ def call(*)
16
+ puts VERSION
17
+ end
18
+ end
19
+
20
+ class ListWorkflows < Dry::CLI::Command
21
+ desc "List workflows on the given repo"
22
+
23
+ argument :owner, required: true
24
+ argument :repo, required: true
25
+
26
+ def call(owner:, repo:)
27
+ workflows = GithubApiClient.new(owner: owner, repo: repo, token: ENV["GH_TOKEN"]).fetch_workflows
28
+ puts "Found #{workflows.size} workflows"
29
+ workflows.each { |workflow| puts workflow[:name] }
30
+ puts
31
+ end
32
+ end
33
+
34
+ class DurationHistory < Dry::CLI::Command
35
+ desc "List the duration of each successful workflow run"
36
+
37
+ argument :owner, required: true
38
+ argument :repo, required: true
39
+ argument :workflow, required: true
40
+
41
+ def call(owner:, repo:, workflow:)
42
+ durations = GithubApiClient.new(owner: owner, repo: repo, token: ENV["GH_TOKEN"]).fetch_workflow_duration_history(workflow)
43
+
44
+ durations_output = CSV.generate do |csv|
45
+ csv << ["Date", "Duration"]
46
+ durations.each do |duration|
47
+ csv << duration
48
+ end
49
+ end
50
+
51
+ puts durations_output
52
+ puts
53
+ end
54
+ end
55
+
56
+ register "version", Version, aliases: ["v", "-v", "--version"]
57
+ register "list-workflows", ListWorkflows
58
+ register "duration-history", DurationHistory
59
+ end
60
+ end
@@ -0,0 +1,54 @@
1
+ require "http"
2
+
3
+ module Ghamma
4
+ class GithubApiClient
5
+ BASE_URL = "https://api.github.com".freeze
6
+
7
+ def initialize(owner:, repo:, token:)
8
+ @repo_base_url = "#{BASE_URL}/repos/#{owner}/#{repo}"
9
+ @authorization_header = "Bearer #{token}"
10
+ end
11
+
12
+ def fetch_workflows
13
+ get("/workflows")
14
+ .fetch("workflows")
15
+ .map do |workflow_json|
16
+ workflow_json.transform_keys(&:to_sym).slice(:id, :name)
17
+ end
18
+ end
19
+
20
+ def fetch_workflow_duration_history(workflow_name)
21
+ workflow_id = get("/workflows").fetch("workflows")
22
+ .find { |workflow| workflow["name"] == workflow_name }
23
+ &.fetch("id", nil)
24
+
25
+ if workflow_id.nil?
26
+ raise "Could not find workflow with name #{workflow_name}"
27
+ end
28
+
29
+ workflow_runs = get(
30
+ "/workflows/#{workflow_id}}/runs",
31
+ {per_page: 100, status: "success", exclude_pull_requests: true}
32
+ ).fetch("workflow_runs")
33
+ .map do |workflow_run|
34
+ run_timing = get("/runs/#{workflow_run["id"]}/timing")
35
+
36
+ [
37
+ workflow_run["created_at"],
38
+ run_timing["run_duration_ms"]
39
+ ]
40
+ end
41
+ end
42
+
43
+ private
44
+
45
+ attr_reader :repo_base_url, :authorization_header
46
+
47
+ def get(resource, params = {})
48
+ HTTP
49
+ .auth(authorization_header)
50
+ .get("#{repo_base_url}/actions#{resource}", params: params)
51
+ .parse
52
+ end
53
+ end
54
+ end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Ghamma
4
- VERSION = "0.1.0"
4
+ VERSION = "0.2.0"
5
5
  end
data/lib/ghamma.rb CHANGED
@@ -1,83 +1,8 @@
1
1
  # frozen_string_literal: true
2
2
 
3
+ require_relative "ghamma/cli"
3
4
  require_relative "ghamma/version"
4
5
 
5
6
  module Ghamma
6
7
  class Error < StandardError; end
7
-
8
- require "csv"
9
- require "http"
10
-
11
- BASE_URL = "https://api.github.com".freeze
12
- OWNER = ARGV[0].freeze
13
- REPOSITORY = ARGV[1].freeze
14
-
15
- def api_url(resource)
16
- "#{BASE_URL}#{resource}"
17
- end
18
-
19
- def get(resource, params = {})
20
- response = HTTP
21
- .auth("Bearer #{ENV["GH_TOKEN"]}")
22
- .get(api_url(resource), params: params)
23
- .body
24
- JSON.parse(response)
25
- end
26
-
27
- def fetch_workflows
28
- response = get "/repos/#{OWNER}/#{REPOSITORY}/actions/workflows"
29
- response["workflows"].map { |json| {id: json["id"], name: json["name"]} }.tap do |workflows|
30
- puts "Found #{workflows.size} workflows"
31
- end
32
- end
33
-
34
- def fetch_workflows_with_runs
35
- fetch_workflows.map do |workflow|
36
- response = get "/repos/#{OWNER}/#{REPOSITORY}/actions/workflows/#{workflow[:id]}/runs",
37
- {per_page: 100, status: "success", exclude_pull_requests: true, created: ">2023-05-01"}
38
- puts "Fetched runs for #{workflow[:name]}"
39
-
40
- next if response["total_count"].zero?
41
-
42
- {
43
- id: workflow[:id],
44
- name: workflow[:name],
45
- runs: response["workflow_runs"].map { |json| {id: json["id"], date: json["created_at"]} }
46
- }
47
- end.compact
48
- end
49
-
50
- def fetch_workflow_duration_metrics
51
- fetch_workflows_with_runs.map do |workflow|
52
- runs_with_timing = workflow[:runs].map do |workflow_run|
53
- response = get "/repos/#{OWNER}/#{REPOSITORY}/actions/runs/#{workflow_run[:id]}/timing"
54
-
55
- {
56
- duration: response["run_duration_ms"],
57
- date: workflow_run[:date]
58
- }
59
- end
60
-
61
- puts "Fetched timings for #{workflow[:name]}"
62
-
63
- {
64
- name: workflow[:name],
65
- runs: runs_with_timing
66
- }
67
- end
68
- end
69
-
70
- metrics = fetch_workflow_duration_metrics
71
-
72
- metrics.each do |workflow_metrics|
73
- puts workflow_metrics[:name]
74
- metrics_table = CSV.generate do |csv|
75
- csv << ["Date", "Duration"]
76
- workflow_metrics[:runs].each do |metric_datum|
77
- csv << [metric_datum[:date], metric_datum[:duration]]
78
- end
79
- end
80
- puts metrics_table
81
- puts
82
- end
83
8
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: ghamma
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.0
4
+ version: 0.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Tony Rowan
@@ -10,6 +10,20 @@ bindir: exe
10
10
  cert_chain: []
11
11
  date: 2023-06-01 00:00:00.000000000 Z
12
12
  dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: dry-cli
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ">="
18
+ - !ruby/object:Gem::Version
19
+ version: '0'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ">="
25
+ - !ruby/object:Gem::Version
26
+ version: '0'
13
27
  - !ruby/object:Gem::Dependency
14
28
  name: http
15
29
  requirement: !ruby/object:Gem::Requirement
@@ -24,6 +38,20 @@ dependencies:
24
38
  - - ">="
25
39
  - !ruby/object:Gem::Version
26
40
  version: '0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: rake
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - ">="
46
+ - !ruby/object:Gem::Version
47
+ version: '0'
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ">="
53
+ - !ruby/object:Gem::Version
54
+ version: '0'
27
55
  - !ruby/object:Gem::Dependency
28
56
  name: standard
29
57
  requirement: !ruby/object:Gem::Requirement
@@ -38,10 +66,25 @@ dependencies:
38
66
  - - ">="
39
67
  - !ruby/object:Gem::Version
40
68
  version: '0'
69
+ - !ruby/object:Gem::Dependency
70
+ name: test-unit
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - ">="
74
+ - !ruby/object:Gem::Version
75
+ version: '0'
76
+ type: :development
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - ">="
81
+ - !ruby/object:Gem::Version
82
+ version: '0'
41
83
  description:
42
84
  email:
43
85
  - trowan812@gmail.com
44
- executables: []
86
+ executables:
87
+ - ghamma
45
88
  extensions: []
46
89
  extra_rdoc_files: []
47
90
  files:
@@ -53,7 +96,10 @@ files:
53
96
  - LICENSE.txt
54
97
  - README.md
55
98
  - Rakefile
99
+ - exe/ghamma
56
100
  - lib/ghamma.rb
101
+ - lib/ghamma/cli.rb
102
+ - lib/ghamma/github_api_client.rb
57
103
  - lib/ghamma/version.rb
58
104
  - sig/ghamma.rbs
59
105
  homepage: https://github.com/tony-rowan/ghamma