jira-cli 0.0.8 → 0.0.9

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
  SHA1:
3
- metadata.gz: e2036d8670e831787e5b06238d5989db70d5d28e
4
- data.tar.gz: 04a472335c54b49ca44dd7af30fe670a61f2863b
3
+ metadata.gz: cde1ac20a643d00b9b6d3308c49a84b94db85281
4
+ data.tar.gz: 807d024db48e5b22661a588aa6290c2ba65c3cfc
5
5
  SHA512:
6
- metadata.gz: 51286f2fa3d9a52b79ad227ae62a646834881226204e66c828ba50c2e6c37bdc60bf494c16d69cdee8ce65b827e2e2355a5d0700ca5ed74f72c091cc6d1e4c5d
7
- data.tar.gz: 623822ac5a21589ee525683829f69c41bc407ba14261b8122d647c28f0de9155894188dd363b49b43760d27d87dd1e61cc35dc921c4ed836406265c9e5d4bc2e
6
+ metadata.gz: a1c9306b45a7f7126bafda539d153d6d20fecff6dd566b7c21007ab8b33f5ec2a3aa2f7f9e1ca80c830c22ae8e4a31c7a72b0afd91378c31da9feeaaba4e401a
7
+ data.tar.gz: 9d0cda918e9e06385c4ae62c5872a506c7c80104a4f250507ef4a1efc143623de42ae4f152d600e4a70836104437b5021cb068701ea3d1b290b259ad3aebd0fd
@@ -18,7 +18,7 @@ module Jira
18
18
  def initialize(args=[], options={}, config={})
19
19
  super
20
20
  Jira::Core.setup
21
- @api = Jira::API.new
21
+ self.api
22
22
  end
23
23
 
24
24
  end
@@ -7,35 +7,62 @@ module Jira
7
7
  def initialize
8
8
  @client = Faraday.new
9
9
  @client.basic_auth(Jira::Core.username, Jira::Core.password)
10
- end
11
10
 
12
- #
13
- # Issue an API GET request and return parsed JSON
14
- #
15
- # @param path [String] API path
16
- #
17
- # @return [JSON] parsed API response
18
- #
19
- def get(path, params={})
20
- response = @client.get(self.endpoint(path), params, self.headers)
21
- return response.body.to_s.from_json
22
- end
23
-
24
- #
25
- # Issue an API POST request and return parsed JSON
26
- #
27
- # @param path [String] API path
28
- # @param params [Hash] params to post
29
- #
30
- # @return [JSON] parsed API response
31
- #
32
- def post(path, params={})
33
- response = @client.post(self.endpoint(path), params, self.headers)
34
- return response.body.to_s.from_json
11
+ self.define_actions
35
12
  end
36
13
 
37
14
  protected
38
15
 
16
+ #
17
+ # Defines the API GET, POST, PUT interaction methods
18
+ #
19
+ def define_actions
20
+ #
21
+ # def method(path, params={})
22
+ #
23
+ # Issue an API GET, POST, or PUT request and return parse JSON
24
+ #
25
+ # @param path [String] API path
26
+ # @param params [Hash] params to send
27
+ #
28
+ # @yield(Hash) yields to a success block
29
+ #
30
+ # @return [JSON] parased API response
31
+ #
32
+ [:get, :post, :put].each do |method|
33
+ self.class.send(:define_method, method) do |path, params=nil, verbose=true, &block|
34
+ params = params.to_json if !params.nil?
35
+ response = @client.send(
36
+ method,
37
+ self.endpoint(path),
38
+ params,
39
+ self.headers
40
+ )
41
+ json = response.body.to_s.from_json
42
+ if self.errorless?(json, verbose)
43
+ block.call(json)
44
+ end
45
+ end
46
+ end
47
+ end
48
+
49
+ #
50
+ # If any, outputs all API errors described by the input JSON
51
+ #
52
+ # @param json [Hash] API response JSON
53
+ # @param verbose [Boolean] true if errors should be output
54
+ #
55
+ # @return [Boolean] true if no errors exist
56
+ #
57
+ def errorless?(json, verbose=true)
58
+ errors = json['errorMessages']
59
+ if !errors.nil?
60
+ puts errors.join('. ') if verbose
61
+ return false
62
+ end
63
+ return true
64
+ end
65
+
39
66
  #
40
67
  # Returns the full JIRA REST API endpoint
41
68
  #
@@ -7,19 +7,15 @@ module Jira
7
7
  if comment.strip.empty?
8
8
  puts "No comment posted."
9
9
  else
10
- json = @api.post("issue/#{ticket}/comment", { body: comment }.to_json)
11
- if json['errorMessages'].nil?
10
+ self.api.post("issue/#{ticket}/comment", { body: comment }) do |json|
12
11
  puts "Successfully posted your comment."
13
- else
14
- puts json['errorMessages'].join('. ')
15
12
  end
16
13
  end
17
14
  end
18
15
 
19
16
  desc "comments", "Lists the comments of the input ticket"
20
17
  def comments(ticket=Jira::Core.ticket)
21
- json = @api.get("issue/#{ticket}")
22
- if json['errorMessages'].nil?
18
+ self.api.get("issue/#{ticket}") do |json|
23
19
  comments = json['fields']['comment']['comments']
24
20
  if comments.count > 0
25
21
  comments.each do |comment|
@@ -34,8 +30,6 @@ module Jira
34
30
  else
35
31
  puts "There are no comments on issue #{ticket}."
36
32
  end
37
- else
38
- puts json['errorMessages'].join('. ')
39
33
  end
40
34
  end
41
35
 
@@ -3,7 +3,12 @@ module Jira
3
3
 
4
4
  desc "describe", "Describes the input ticket"
5
5
  def describe(ticket=Jira::Core.ticket)
6
- puts description(ticket.strip, false, true)
6
+ if Jira::Core.ticket?(ticket)
7
+ output = description(ticket.strip, false, true)
8
+ puts output if !output.strip.empty?
9
+ else
10
+ puts "The ticket #{ticket} is not a valid JIRA ticket."
11
+ end
7
12
  end
8
13
 
9
14
  desc "all", "Describes all local branches that match JIRA ticketing syntax"
@@ -30,7 +35,7 @@ module Jira
30
35
  # asynchronously fetch and describe tickets
31
36
  output = ""
32
37
  threads = []
33
- if Jira::Core.ticket?(tickets[:current])
38
+ if !tickets[:current].nil?
34
39
  threads << Thread.new{ puts description(tickets[:current], true) }
35
40
  end
36
41
  mutex = Mutex.new
@@ -57,8 +62,7 @@ module Jira
57
62
  # @return [String] formatted summary string
58
63
  #
59
64
  def description(ticket, star=false, verbose=false)
60
- json = @api.get("issue/#{ticket}")
61
- if json['errorMessages'].nil?
65
+ self.api.get("issue/#{ticket}", nil, verbose) do |json|
62
66
  summary = json['fields']['summary']
63
67
  status = json['fields']['status']['name']
64
68
  assignee = json['fields']['assignee']['name']
@@ -67,11 +71,8 @@ module Jira
67
71
  ("(" + Jira::Format.user(assignee) + ")").ljust(20) +
68
72
  Jira::Format.status(status).ljust(26) +
69
73
  Jira::Format.summary(summary)
70
- elsif verbose
71
- return json['errorMessages'].join('. ')
72
- else
73
- return ""
74
74
  end
75
+ return ""
75
76
  end
76
77
 
77
78
  end
@@ -4,11 +4,8 @@ module Jira
4
4
  desc "log", "Logs work against the input ticket"
5
5
  def log(ticket=Jira::Core.ticket)
6
6
  time_spent = self.cli.ask("Time spent on #{ticket}: ")
7
- json = @api.post("issue/#{ticket}/worklog", { timeSpent: time_spent }.to_json)
8
- if json['errorMessages'].nil?
7
+ self.api.post("issue/#{ticket}/worklog", { timeSpent: time_spent }) do |json|
9
8
  puts "Successfully logged #{time_spent} on #{ticket}."
10
- else
11
- puts json['errorMessages'].join('. ')
12
9
  end
13
10
  end
14
11
 
@@ -0,0 +1,111 @@
1
+ module Jira
2
+ class CLI < Thor
3
+
4
+ desc "new", "Creates a new ticket in JIRA and checks out the git branch"
5
+ def new
6
+ self.api.get("issue/createmeta") do |meta|
7
+ # determine project
8
+ project = self.select_project(meta)
9
+ break if project.empty?
10
+
11
+ # determine issue type
12
+ issue_type = self.select_issue_type(project)
13
+ return if issue_type.empty?
14
+
15
+ # determine summary and description
16
+ summary = self.cli.ask("\nSummary: ")
17
+ description = self.cli.ask("Description:")
18
+
19
+ # determine api parameters
20
+ params = {
21
+ fields: {
22
+ project: { id: project[:id] },
23
+ issuetype: { id: issue_type },
24
+ summary: summary,
25
+ description: description
26
+ }
27
+ }
28
+
29
+ # post issue to server
30
+ self.api.post("issue", params) do |json|
31
+ ticket = json['key']
32
+ `git checkout -b #{ticket} 2> /dev/null`
33
+ puts "\nTicket and branch #{Jira::Format.ticket(ticket)} created."
34
+ return
35
+ end
36
+ end
37
+ puts "No ticket created."
38
+ end
39
+
40
+ protected
41
+
42
+ #
43
+ # Given the creation metadata, prompts the user for the project to use,
44
+ # then return the project data hash
45
+ #
46
+ # @param json [Hash] creation metadata
47
+ #
48
+ # @return [Hash] selected project's metadata
49
+ #
50
+ def select_project(json)
51
+ projects = {}
52
+ json['projects'].each do |project|
53
+ data = {
54
+ id: project['id'],
55
+ issues: project['issuetypes']
56
+ }
57
+ projects[project['name']] = data
58
+ end
59
+ projects['Cancel'] = nil
60
+
61
+ self.cli.choose do |menu|
62
+ menu.index = :number
63
+ menu.index_suffix = ") "
64
+ menu.header = "Select a project to create issue under"
65
+ menu.prompt = "Project: "
66
+ projects.keys.each do |choice|
67
+ menu.choice choice do
68
+ project_data = projects[choice]
69
+ if !project_data.nil?
70
+ return project_data
71
+ end
72
+ end
73
+ end
74
+ end
75
+ return {}
76
+ end
77
+
78
+ #
79
+ # Given the project metadata, prompts the user for the issue type to use
80
+ # and returns the selected issue type.
81
+ #
82
+ # @param project_data [Hash] project metadata
83
+ #
84
+ # @return [String] selected issue type
85
+ #
86
+ def select_issue_type(project_data)
87
+ issue_types = {}
88
+ project_data[:issues].each do |issue_type|
89
+ issue_types[issue_type['name']] = issue_type['id']
90
+ end
91
+ issue_types['Cancel'] = nil
92
+
93
+ self.cli.choose do |menu|
94
+ menu.index = :number
95
+ menu.index_suffix = ") "
96
+ menu.header = "\nSelect an issue type"
97
+ menu.prompt = "Issue type: "
98
+ issue_types.keys.each do |choice|
99
+ menu.choice choice do
100
+ issue_type_id = issue_types[choice]
101
+ if !issue_type_id.nil?
102
+ return issue_type_id
103
+ end
104
+ end
105
+ end
106
+ end
107
+ return ""
108
+ end
109
+
110
+ end
111
+ end
@@ -0,0 +1,19 @@
1
+ module Jira
2
+ class CLI < Thor
3
+
4
+ desc "rename", "Updates the summary of the input ticket"
5
+ def rename(ticket=Jira::Core.ticket)
6
+ self.describe(ticket)
7
+ summary = self.cli.ask("What should the new ticket summary be?")
8
+ if !summary.strip.empty?
9
+ params = { fields: { summary: summary } }
10
+ self.api.put("issue/#{ticket}", params) do |json|
11
+ puts "Successfully updated ticket #{ticket}'s summary."
12
+ end
13
+ else
14
+ puts "No change made to ticket #{ticket}."
15
+ end
16
+ end
17
+
18
+ end
19
+ end
@@ -3,26 +3,26 @@ module Jira
3
3
 
4
4
  desc "transition", "Transitions the input ticket to the next state"
5
5
  def transition(ticket=Jira::Core.ticket)
6
- json = @api.get("issue/#{ticket}/transitions")
7
-
8
- options = {}
9
- json['transitions'].each do |transition|
10
- options[transition['name']] = transition['id']
11
- end
12
- options['Cancel'] = nil
6
+ self.api.get("issue/#{ticket}/transitions") do |json|
7
+ options = {}
8
+ json['transitions'].each do |transition|
9
+ options[transition['to']['name']] = transition['id']
10
+ end
11
+ options['Cancel'] = nil
13
12
 
14
- self.cli.choose do |menu|
15
- menu.index = :number
16
- menu.index_suffix = ") "
17
- menu.header = "Transitions Available For #{ticket}"
18
- menu.prompt = "Select a transition: "
19
- options.keys.each do |choice|
20
- menu.choice choice do
21
- transition_id = options[choice]
22
- if transition_id.nil?
23
- puts "No transition was performed on #{ticket}."
24
- else
25
- self.api_transition(ticket, transition_id, choice)
13
+ self.cli.choose do |menu|
14
+ menu.index = :number
15
+ menu.index_suffix = ") "
16
+ menu.header = "Transition #{Jira::Format.ticket(ticket)} to:"
17
+ menu.prompt = "Transition to: "
18
+ options.keys.each do |choice|
19
+ menu.choice choice do
20
+ transition_id = options[choice]
21
+ if transition_id.nil?
22
+ puts "No transition was performed on #{ticket}."
23
+ else
24
+ self.api_transition(ticket, transition_id, choice)
25
+ end
26
26
  end
27
27
  end
28
28
  end
@@ -32,15 +32,10 @@ module Jira
32
32
  protected
33
33
 
34
34
  def api_transition(ticket, transition, description)
35
- json = @api.post(
36
- "issue/#{ticket}/transitions",
37
- { transition: { id: transition } }.to_json
38
- )
39
- if json.empty?
35
+ params = { transition: { id: transition } }
36
+ self.api.post("issue/#{ticket}/transitions", params) do |json|
40
37
  puts "Successfully performed transition (#{description}) "\
41
38
  "on ticket #{ticket}."
42
- else
43
- puts json['errorMessages'].join('. ')
44
39
  end
45
40
  end
46
41
 
@@ -1,5 +1,5 @@
1
1
  module Jira
2
2
 
3
- VERSION = "0.0.8"
3
+ VERSION = "0.0.9"
4
4
 
5
5
  end
@@ -15,15 +15,20 @@ module Jira
15
15
  @highline ||= ::HighLine.new
16
16
  end
17
17
 
18
+ #
19
+ # @return [Jira::API] Jira API class
20
+ #
21
+ def api
22
+ @api ||= Jira::API.new
23
+ end
24
+
18
25
  end
19
26
  end
20
27
 
21
28
  class String
22
29
 
23
30
  def from_json
24
- JSON.parse(self)
25
- rescue
26
- {}
31
+ JSON.parse(self) rescue {}
27
32
  end
28
33
 
29
34
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: jira-cli
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.8
4
+ version: 0.0.9
5
5
  platform: ruby
6
6
  authors:
7
7
  - Darren Lin Cheng
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2013-11-07 00:00:00.000000000 Z
11
+ date: 2013-11-11 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: thor
@@ -66,6 +66,8 @@ files:
66
66
  - lib/jira/commands/describe.rb
67
67
  - lib/jira/commands/install.rb
68
68
  - lib/jira/commands/log.rb
69
+ - lib/jira/commands/new.rb
70
+ - lib/jira/commands/rename.rb
69
71
  - lib/jira/commands/transition.rb
70
72
  - lib/jira/commands/version.rb
71
73
  - lib/jira/constants.rb