github_workflow 0.3.9 → 0.4.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: c0d0091f831042df6bf6521994c7e84ec07b330acf6bb0441032a10cd74cb8b0
4
- data.tar.gz: 9a47a0432865d512d66b180b6b53ca7758738d9573aaa56065279c2d5bc9d80e
3
+ metadata.gz: 8e9f6a6dfe205f986f1d69b2a778ca8aaf008833423cbde6e664818d90c7c0e0
4
+ data.tar.gz: 1f3dce21f39ca0e0ca4cba5ddcafa0c1817b2e0fd4d8e5ef2de82b6abd4a6f21
5
5
  SHA512:
6
- metadata.gz: e68ef334f027cc1c297af90396cfef2da209d2011ff138359a9d5774b50ad0a3325240dc94636f33083e5072138a5e2b5c63738ef2a7ef9ef8fee8634601aaf8
7
- data.tar.gz: ffb8cdd1ac843d06894310e226cf42e11a2bc0fc2976e5489e069e0ceff972aa325f7e7fa82067a6ba7fa14ee77f407029abe4a965912367f674e73e41e25223
6
+ metadata.gz: a4b8055a935171f2c1a9e694ada8ca0b78704e4c49f5880745f4c1920023841fcd94d1819a39bdd26bee89b35a1a6c508de49f16538b45bd261dad39b0798d97
7
+ data.tar.gz: 824bc8e9cfadf38d68a9e6b34d22a715eeaa08c3dc260ce7637aef8e10f7cc89bfa2313992dd8a0619f88c4908207c68268c04551d3867e48c6de354ea0892e4
data/README.md CHANGED
@@ -1,18 +1,12 @@
1
- # Configuration
1
+ # Setup
2
2
 
3
- Each repository should contain its own config (`.github_workflow`), which should look like this:
4
- ```
5
- {
6
- "oauth_token": "TOKEN",
7
- "user_and_repo": "ORG/REPO",
8
- "trello_key": "KEY",
9
- "trello_token": "TOKEN",
10
- "trello_board_id": "BOARD_ID",
11
- "trello_platform_board_id": "BOARD_ID"
12
- }
13
- ```
14
- Optionally, all general information except `user_and_repo` could be extracted to global config in your home directory
15
- with the same name (~/.github_workflow)
3
+ Install the [GitHub cli](https://cli.github.com/manual/)
4
+
5
+ `brew install gh`
6
+
7
+ login to the cli
8
+
9
+ `gh login`
16
10
 
17
11
  # Github Workflow
18
12
 
@@ -18,9 +18,7 @@ Gem::Specification.new do |spec|
18
18
  spec.require_paths = ["lib"]
19
19
 
20
20
  spec.add_dependency "thor", "~> 1.0.1"
21
- spec.add_dependency "faraday", "~> 0.11", "< 2.0"
22
21
  spec.add_dependency "terminal-table", "~> 1.5"
23
- spec.add_dependency "ruby-trello", "~> 2.1"
24
22
 
25
23
  spec.add_development_dependency "bundler"
26
24
  spec.add_development_dependency "pry"
@@ -1,61 +1,22 @@
1
1
  require "rubygems"
2
2
  require "pry"
3
- require "faraday"
4
3
  require "thor"
5
4
  require "open3"
6
5
  require "json"
7
6
  require "terminal-table"
8
- require "trello"
7
+ require_relative "gh_cli_client.rb"
9
8
 
10
9
  module GithubWorkflow
11
10
  class Cli < Thor
12
11
  PROCEED_TEXT = "Proceed? [y,yes]: ".freeze
13
- CONFIG_FILE_NAME = ".github_workflow".freeze
14
- GITHUB_CONFIG = <<~TEXT
15
- {
16
- "oauth_token": "TOKEN",
17
- "user_and_repo": "ORG/REPO",
18
- "trello_key": "KEY",
19
- "trello_token": "TOKEN",
20
- "trello_board_id": "BOARD_ID",
21
- "trello_platform_board_id": "BOARD_ID"
22
- }
23
- TEXT
24
12
 
25
13
  include Thor::Actions
26
14
 
27
- default_task :trello
28
-
29
- desc "trello", "Create issue from card"
30
- method_option :card_number, aliases: "-i", type: :string, required: true
31
- def trello
32
- ensure_github_config_present
33
- init_trello
34
- set_trello_card(type: nil)
35
- create_issue_from_trello_card
36
- stash
37
- rebase_main
38
- create_branch
39
- stash_pop
40
- end
41
-
42
- desc "platform", "Create issue from card"
43
- method_option :card_number, aliases: "-i", type: :string, required: true
44
- def platform
45
- ensure_github_config_present
46
- init_trello
47
- set_trello_card(type: :platform)
48
- create_issue_from_trello_card
49
- stash
50
- rebase_main
51
- create_branch
52
- stash_pop
53
- end
15
+ default_task :start
54
16
 
55
17
  desc "start", "Create branch named with issue number and issue title"
56
18
  method_option :issue_id, aliases: "-i", type: :string, required: true
57
19
  def start
58
- ensure_github_config_present
59
20
  stash
60
21
  rebase_main
61
22
  create_branch
@@ -65,7 +26,6 @@ module GithubWorkflow
65
26
  desc "create_pr", "Convert Issue to Pull Request"
66
27
  method_option :base_branch, aliases: "-b", type: :string
67
28
  def create_pr
68
- ensure_github_config_present
69
29
  ensure_origin_exists
70
30
  convert_issue_to_pr
71
31
  end
@@ -73,16 +33,14 @@ module GithubWorkflow
73
33
  desc "push_and_pr", "Push branch to origin and convert Issue to Pull Request"
74
34
  method_option :base_branch, aliases: "-b", type: :string
75
35
  def push_and_pr
76
- ensure_github_config_present
77
36
  push_and_set_upstream
78
37
  convert_issue_to_pr
79
38
  end
80
39
 
81
40
  desc "status", "Check PR CI status"
82
41
  def status
83
- ensure_github_config_present
84
42
  ensure_origin_exists
85
- response = JSON.parse(github_client.get("repos/#{user_and_repo}/statuses/#{current_branch}").body)
43
+ response = github_client.get_statuses
86
44
 
87
45
  if response.empty?
88
46
  alert "No statuses yet. Have you pushed your branch?"
@@ -104,21 +62,20 @@ module GithubWorkflow
104
62
 
105
63
  desc "info", "Print out issue description"
106
64
  def info
107
- ensure_github_config_present
108
- puts get_issue(issue_number_from_branch)["body"]
65
+ issue = github_client.get_issue(issue_number_from_branch)
66
+ puts "#{issue["html_url"]}\n\n"
67
+ puts "[##{issue["number"]}] #{issue["title"]}\n"
68
+ puts issue["body"]
109
69
  end
110
70
 
111
71
  desc "open", "Open issue or PR in browser"
112
72
  def open
113
- ensure_github_config_present
114
- response = JSON.parse(github_client.get("repos/#{user_and_repo}/issues/#{issue_number_from_branch}").body)
115
- `/usr/bin/open -a "/Applications/Google Chrome.app" '#{response["html_url"]}'`
73
+ open_url(github_client.get_issue(issue_number_from_branch)["html_url"])
116
74
  end
117
75
 
118
76
  desc "create_and_start", "Create and start issue"
119
77
  method_option :name, aliases: "-m", type: :string, required: true
120
78
  def create_and_start
121
- ensure_github_config_present
122
79
  create_issue
123
80
  end
124
81
 
@@ -147,8 +104,7 @@ module GithubWorkflow
147
104
 
148
105
  desc "reviews", "Displays count of requested reviews for each user"
149
106
  def reviews
150
- ensure_github_config_present
151
- reviewers = get_prs_list.map { |pr| pr["requested_reviewers"].map { |r| r["login"] } }.flatten
107
+ reviewers = github_client.get_prs_list.map { |pr| pr["requested_reviewers"].map { |r| r["login"] } }.flatten
152
108
  reviewer_counts = reviewers.group_by { |i| i }.map { |k, v| [k, v.count] }
153
109
 
154
110
  if reviewer_counts.any?
@@ -170,16 +126,8 @@ module GithubWorkflow
170
126
  end
171
127
 
172
128
  no_tasks do
173
- def get_issue(id)
174
- JSON.parse(github_client.get("repos/#{user_and_repo}/issues/#{id}").body)
175
- end
176
-
177
- def get_pr(id)
178
- JSON.parse(github_client.get("repos/#{user_and_repo}/pulls/#{id}").body)
179
- end
180
-
181
- def get_prs_list
182
- JSON.parse(github_client.get("repos/#{user_and_repo}/pulls?per_page=100").body)
129
+ def open_url(url)
130
+ `/usr/bin/open -a "/Applications/Google Chrome.app" '#{url}'`
183
131
  end
184
132
 
185
133
  def create_branch
@@ -194,126 +142,21 @@ module GithubWorkflow
194
142
  end
195
143
  end
196
144
 
197
- def create_issue_from_trello_card
198
- say_info("Creating issue")
199
-
200
- issue_params = {
201
- title: trello_card.name,
202
- body: issue_body_from_trello_card,
203
- assignees: [current_github_username],
204
- labels: trello_card.labels.map(&:name)
205
- }
206
-
207
- response = JSON.parse(github_client.post("repos/#{user_and_repo}/issues", issue_params.to_json).body)
208
-
209
- @issue_id = response["number"]
210
-
211
- github_client.post("/repos/#{user_and_repo}/issues/#{@issue_id}/comments", { body: trello_card.short_url }.to_json)
212
- trello_card.add_attachment response["html_url"]
213
- end
214
-
215
- def issue_body_from_trello_card
216
- [trello_card.desc, trello_deploy_note, trello_product_review_type, trello_pm].compact.join("\n\n")
217
- end
218
-
219
- def trello_pm
220
- custom_field = trello_card.custom_field_items.detect { |cfi| cfi.custom_field.name == "PM" }
221
-
222
- if custom_field.present?
223
- "**Responsible:** #{custom_field.option_value['text']}"
224
- end
225
- end
226
-
227
- def trello_deploy_note
228
- custom_field = trello_card.custom_field_items.detect { |cfi| cfi.custom_field.name == "Deploy Note" }
229
-
230
- if custom_field.present?
231
- "**Deploy Note:** #{custom_field.value['text']}"
232
- end
233
- end
234
-
235
- def trello_product_review_type
236
- custom_field = trello_card.custom_field_items.detect { |cfi| cfi.custom_field.name == "Product Review" }
237
-
238
- if custom_field.present?
239
- "**Product Review:** #{custom_field.option_value['text']}"
240
- end
241
- end
242
-
243
- def current_github_username
244
- JSON.parse(github_client.get("user").body)["login"]
245
- end
246
-
247
- def set_trello_card(type:)
248
- say_info("Fetching trello card")
249
-
250
- trello_board =
251
- if type
252
- Trello::Board.find(project_config["trello_#{type}_board_id"])
253
- else
254
- Trello::Board.find(project_config["trello_board_id"])
255
- end
256
-
257
- @trello_card = trello_board.find_card(options["card_number"].to_i)
258
- end
259
-
260
- def trello_card
261
- @trello_card
262
- end
263
-
264
- def ensure_github_config_present
265
- if (JSON.parse(GITHUB_CONFIG).keys - project_config.keys).any?
266
- failure("Please add `.github_workflow` file containing:\n#{GITHUB_CONFIG}")
267
- end
268
- end
269
-
270
- def init_trello
271
- Trello.configure do |config|
272
- config.developer_public_key = project_config["trello_key"]
273
- config.member_token = project_config["trello_token"]
274
- end
275
- end
276
-
277
- def project_config
278
- @project_config ||=
279
- begin
280
- global_config_path = Pathname.new(Dir.home).join(CONFIG_FILE_NAME)
281
- result = File.exists?(global_config_path) ? JSON.parse(File.read(global_config_path)) : {}
282
- local_config_data = JSON.parse(File.read(CONFIG_FILE_NAME))
283
- result.merge(local_config_data)
284
- rescue
285
- {}
286
- end
287
- end
288
-
289
- def oauth_token
290
- project_config["oauth_token"]
291
- end
292
-
293
- def user_and_repo
294
- project_config["user_and_repo"]
295
- end
296
-
297
145
  def push_and_set_upstream
298
146
  `git rev-parse --abbrev-ref HEAD | xargs git push origin -u`
299
147
  end
300
148
 
301
149
  def create_issue
302
- github_client.post(
303
- "repos/#{user_and_repo}/issues",
304
- JSON.generate(
305
- {
306
- title: options[:name]
307
- }
308
- )
150
+ github_client.create_issue(
151
+ title: options[:name]
309
152
  ).tap do |response|
310
- if response.success?
153
+ if response["number"]
311
154
  pass("Issue created")
312
- @issue_id = JSON.parse(response.body)["number"]
155
+ @issue_id = response["number"]
313
156
  start
314
157
  else
315
158
  alert("An error occurred when creating issue:")
316
- alert("#{response.status}: #{JSON.parse(response.body)['message']}")
159
+ alert("#{response['message']}")
317
160
  end
318
161
  end
319
162
  end
@@ -323,22 +166,17 @@ module GithubWorkflow
323
166
  end
324
167
 
325
168
  def convert_issue_to_pr
326
- github_client.post(
327
- "repos/#{user_and_repo}/pulls",
328
- JSON.generate(
329
- {
330
- head: current_branch,
331
- base: options[:base_branch] || "main",
332
- issue: issue_number_from_branch.to_i
333
- }
334
- )
169
+ github_client.convert_issue_to_pr(
170
+ issue_number_from_branch.to_i,
171
+ head: current_branch,
172
+ base: options[:base_branch] || "main",
335
173
  ).tap do |response|
336
- if response.success?
174
+ if response["url"]
337
175
  pass("Issue converted to Pull Request")
338
- say_info(JSON.parse(response.body)["url"])
176
+ say_info(response["html_url"])
339
177
  else
340
178
  alert("An error occurred when creating PR:")
341
- alert("#{response.status}: #{JSON.parse(response.body)['message']}")
179
+ alert("#{response['message']}")
342
180
  end
343
181
  end
344
182
  end
@@ -356,16 +194,12 @@ module GithubWorkflow
356
194
  end
357
195
 
358
196
  def branch_name_for_issue_number
359
- issue = JSON.parse(github_client.get("repos/#{user_and_repo}/issues/#{issue_id}").body)
197
+ issue = github_client.get_issue(issue_id)
360
198
  "#{issue['number']}_#{issue['title'].strip.downcase.gsub(/[^a-zA-Z0-9]/, '_').squeeze("_")}"
361
199
  end
362
200
 
363
201
  def github_client
364
- Faraday.new(url: "https://api.github.com") do |faraday|
365
- faraday.request :url_encoded
366
- faraday.adapter Faraday.default_adapter
367
- faraday.authorization :Bearer, oauth_token
368
- end
202
+ @gh_client ||= GhCliClient.new
369
203
  end
370
204
 
371
205
  def rebase_main
@@ -400,7 +234,7 @@ module GithubWorkflow
400
234
  @merged_pr_branches ||=
401
235
  pr_branches.map do |branch|
402
236
  id = branch.split("_")[0].to_i
403
- merged = !!get_pr(id)["merged"]
237
+ merged = !!github_client.get_pr(id)["merged"]
404
238
  print merged ? "✅ " : "❌ "
405
239
  puts " #{branch}"
406
240
  merged ? branch : nil
@@ -412,7 +246,7 @@ module GithubWorkflow
412
246
  end
413
247
 
414
248
  def commits_for_range
415
- JSON.parse(github_client.get("repos/#{user_and_repo}/compare/#{options[:commit_range]}").body)
249
+ github_client.commits_for_range(options[:commit_range])
416
250
  end
417
251
 
418
252
  def pull_request_in_commit_range
@@ -422,13 +256,11 @@ module GithubWorkflow
422
256
 
423
257
  prs = pr_ids.map do |id|
424
258
  say_info("Fetching Pull Request ##{id}")
425
- pr = github_client.get("repos/#{user_and_repo}/pulls/#{id}")
259
+ pr = github_client.get_pr(id)
426
260
 
427
- if pr.status == 404
428
- JSON.parse(github_client.get("repos/#{user_and_repo}/issues/#{id}").body)
429
- else
430
- JSON.parse(pr.body)
431
- end
261
+ next pr if pr["number"]
262
+
263
+ github_client.get_issue(id)
432
264
  end
433
265
  end
434
266
 
@@ -0,0 +1,41 @@
1
+
2
+ class GhCliClient
3
+
4
+ def get_issue(id)
5
+ request("'repos/{owner}/{repo}/issues/#{id}'")
6
+ end
7
+
8
+ def get_pr(id)
9
+ request("'repos/{owner}/{repo}/pulls/#{id}'")
10
+ end
11
+
12
+ def get_prs_list
13
+ request("'repos/{owner}/{repo}/pulls?per_page=100'")
14
+ end
15
+
16
+ def create_issue(title:, body: '')
17
+ request("'repos/{owner}/{repo}/issues'", args: {title: title, body: body})
18
+ end
19
+
20
+ def convert_issue_to_pr(id, head:, base:)
21
+ request("'repos/{owner}/{repo}/pulls'", args: {issue: id.to_i, head: head, base: base})
22
+ end
23
+
24
+ def commits_for_range(commit_range)
25
+ # https://docs.github.com/en/rest/commits/commits#compare-two-commits
26
+ request("'repos/{owner}/{repo}/compare/#{commit_range}'")
27
+ end
28
+
29
+ def get_statuses(branch: '{branch}')
30
+ request("'repos/{owner}/{repo}/statuses/#{branch}'")
31
+ end
32
+
33
+ protected
34
+
35
+ def request(url, args: {})
36
+ arg_params = args.map{ |k,v| "-F '#{k}'='#{v}'" }.join(' ')
37
+ response = `gh api #{url} #{arg_params}`
38
+ parsed = JSON.parse(response)
39
+ parsed
40
+ end
41
+ end
@@ -1,3 +1,3 @@
1
1
  module GithubWorkflow
2
- VERSION = "0.3.9"
2
+ VERSION = "0.4.0"
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: github_workflow
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.3.9
4
+ version: 0.4.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Ben Liscio
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2022-03-16 00:00:00.000000000 Z
11
+ date: 2022-05-24 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: thor
@@ -24,26 +24,6 @@ dependencies:
24
24
  - - "~>"
25
25
  - !ruby/object:Gem::Version
26
26
  version: 1.0.1
27
- - !ruby/object:Gem::Dependency
28
- name: faraday
29
- requirement: !ruby/object:Gem::Requirement
30
- requirements:
31
- - - "~>"
32
- - !ruby/object:Gem::Version
33
- version: '0.11'
34
- - - "<"
35
- - !ruby/object:Gem::Version
36
- version: '2.0'
37
- type: :runtime
38
- prerelease: false
39
- version_requirements: !ruby/object:Gem::Requirement
40
- requirements:
41
- - - "~>"
42
- - !ruby/object:Gem::Version
43
- version: '0.11'
44
- - - "<"
45
- - !ruby/object:Gem::Version
46
- version: '2.0'
47
27
  - !ruby/object:Gem::Dependency
48
28
  name: terminal-table
49
29
  requirement: !ruby/object:Gem::Requirement
@@ -58,20 +38,6 @@ dependencies:
58
38
  - - "~>"
59
39
  - !ruby/object:Gem::Version
60
40
  version: '1.5'
61
- - !ruby/object:Gem::Dependency
62
- name: ruby-trello
63
- requirement: !ruby/object:Gem::Requirement
64
- requirements:
65
- - - "~>"
66
- - !ruby/object:Gem::Version
67
- version: '2.1'
68
- type: :runtime
69
- prerelease: false
70
- version_requirements: !ruby/object:Gem::Requirement
71
- requirements:
72
- - - "~>"
73
- - !ruby/object:Gem::Version
74
- version: '2.1'
75
41
  - !ruby/object:Gem::Dependency
76
42
  name: bundler
77
43
  requirement: !ruby/object:Gem::Requirement
@@ -130,6 +96,7 @@ files:
130
96
  - bin/github_workflow
131
97
  - github_workflow.gemspec
132
98
  - lib/github_workflow/cli.rb
99
+ - lib/github_workflow/gh_cli_client.rb
133
100
  - lib/github_workflow/version.rb
134
101
  homepage: https://github.com/daisybill/github_workflow
135
102
  licenses: