ki_pivotal 0.0.3 → 0.0.4

Sign up to get free protection for your applications and to get access to all the features.
data/bin/ki_pivotal CHANGED
@@ -26,18 +26,96 @@ version KiPivotal::VERSION
26
26
  desc 'Initialise config files'
27
27
  command :init do |c|
28
28
  c.action do |global_options,options,args|
29
- Kiseru::Config[:ki_pivotal].write('api_token', KiPivotal::Interactive.repeatedly_ask("Please enter your Pivotal Tracker API token.\n This can be found at the bottom of your 'Profile' page.\n Token"))
30
- end
29
+ config = Kiseru::Config[:ki_pivotal]
30
+ config.write('api_token', KiPivotal::Interactive.repeatedly_ask("Please enter your Pivotal Tracker API token.\n This can be found at the bottom of your 'Profile' page.\n Token"))
31
+ $stdout.puts "Initialized config file at #{config.path}".green
32
+ end
31
33
  end
32
34
 
33
35
  desc 'Get projects'
34
36
  command :projects do |c|
35
- c.action do |global_options,options,args|
37
+ c.action do |global_options, options, args|
36
38
  pretty = $stdout.tty?
37
39
  $stdout.puts KiPivotal::Api.new.projects(:pretty => pretty)
38
40
  end
39
41
  end
40
42
 
43
+ desc 'Get stories'
44
+ command :stories do |c|
45
+ c.desc "The project ID"
46
+ c.flag [:p, :project]
47
+ c.desc "Interactive mode"
48
+ c.switch [:i, :interactive]
49
+ c.action do |global_options, options, args|
50
+ if options[:project]
51
+ project_id = options[:project]
52
+ else
53
+ if options[:i]
54
+ project_id = KiPivotal::Interactive.select_project("Which project would you like to view the stories of?")
55
+ else
56
+ projects = MultiJson.load(KiPivotal::Api.new.projects)
57
+ $stderr.puts "\n Stories cannot be retrieved without specifying which project to retrieve from:"
58
+ $stderr.puts " * The ID of a chosen project may be specified with --project=<ID>"
59
+ $stderr.puts " * A project may be chosen interactively by using the switch -i."
60
+ $stderr.puts "\n Available projects:"
61
+
62
+ projects.each { |project| $stderr.puts " #{project['id']} ".green + " #{project['name']}" }
63
+
64
+ $stderr.puts
65
+ raise "No project given"
66
+ end
67
+ end
68
+
69
+ $stdout.puts KiPivotal::Api.new.stories_in_project(project_id, :pretty => $stdout.tty?)
70
+ end
71
+ end
72
+
73
+ desc 'Get a story'
74
+ command :story do |c|
75
+ c.desc "The story ID"
76
+ c.flag :id
77
+ c.desc "The project ID"
78
+ c.flag [:p, :project]
79
+ c.desc "Interactive mode"
80
+ c.switch [:i, :interactive]
81
+ c.action do |global_options, options, args|
82
+ unless project_id = options[:project]
83
+ if options[:i]
84
+ project_id = KiPivotal::Interactive.select_project("Which project would you like to retrieve the story from?")
85
+ else
86
+ projects = MultiJson.load(KiPivotal::Api.new.projects)
87
+ $stderr.puts "\n A Story cannot be retrieved without specifying which project to retrieve from:"
88
+ $stderr.puts " * The ID of a chosen project may be specified with --project=<ID>"
89
+ $stderr.puts " * A project may be chosen interactively by using the switch -i."
90
+ $stderr.puts "\n Available projects:"
91
+
92
+ projects.each { |project| $stderr.puts " #{project['id']} ".green + " #{project['name']}" }
93
+
94
+ $stderr.puts
95
+ raise "No project given"
96
+ end
97
+ end
98
+ unless story_id = options[:id]
99
+ if options[:i]
100
+ story_id = KiPivotal::Interactive.select_story(project_id, "Which story would you like to view?")
101
+ else
102
+ stories = MultiJson.load(KiPivotal::Api.new.stories_in_project(project_id))
103
+ $stderr.puts "\n You cannot retrieve a story without specifying the story ID:"
104
+ $stderr.puts " * The ID may be specified with --id=<ID>"
105
+ $stderr.puts " * A story may be chosen interactively by using the switch -i."
106
+ $stderr.puts "\n Available stories:"
107
+
108
+ stories.each { |story| $stderr.puts " #{story['id']} ".green + " #{story['name']}" }
109
+
110
+ $stderr.puts
111
+ raise "No story ID given"
112
+ end
113
+ end
114
+ $stdout.puts KiPivotal::Api.new.story_in_project(story_id, project_id, :pretty => $stdout.tty?)
115
+ end
116
+ end
117
+
118
+
41
119
  desc 'Create a story'
42
120
  command :new_story do |c|
43
121
  c.desc "The project ID"
@@ -46,27 +124,32 @@ command :new_story do |c|
46
124
  c.flag [:f, :file]
47
125
  c.desc "Interactive mode"
48
126
  c.switch [:i, :interactive]
49
- c.action do |global_options,options,args|
127
+ c.action do |global_options, options, args|
50
128
  # When we have received JSON via a pipe/file
51
129
  # interactive mode should allow a missing
52
130
  # project ID to be specified.
53
131
  if options[:f] || !$stdin.tty?
54
132
  story_json = options[:f] ? File.read(options[:f]) : $stdin.read
55
133
  unless project_id = options[:project]
56
- projects = MultiJson.load(KiPivotal::Api.new.projects)
57
- if options[:i]
58
- $stdin = STDIN.reopen('/dev/tty')
59
- project_id = KiPivotal::Interactive.select_project
60
- else
61
- $stderr.puts "\n A story cannot be created without specifying which project to create it under:"
62
- $stderr.puts " * The ID of a chosen project may be specified with --project=<ID>"
63
- $stderr.puts " * A project may be chosen interactively by using the switch -i."
64
- $stderr.puts "\n Available projects:"
65
-
66
- projects.each { |project| $stderr.puts " #{project['id']} ".green + " #{project['name']}" }
67
-
68
- $stderr.puts
69
- raise "No project given"
134
+ # Check the json for a 'project_id' attribute for template story niceness.
135
+ json = MultiJson.load(story_json)
136
+ project_id = json['project_id']
137
+ if project_id.nil?
138
+ if options[:i]
139
+ $stdin = STDIN.reopen('/dev/tty')
140
+ project_id = KiPivotal::Interactive.select_project("Which project should this story be created under?")
141
+ else
142
+ projects = MultiJson.load(KiPivotal::Api.new.projects)
143
+ $stderr.puts "\n A story cannot be created without specifying which project to create it under:"
144
+ $stderr.puts " * The ID of a chosen project may be specified with --project=<ID>"
145
+ $stderr.puts " * A project may be chosen interactively by using the switch -i."
146
+ $stderr.puts "\n Available projects:"
147
+
148
+ projects.each { |project| $stderr.puts " #{project['id']} ".green + " #{project['name']}" }
149
+
150
+ $stderr.puts
151
+ raise "No project given"
152
+ end
70
153
  end
71
154
  end
72
155
  # When there is no JSON provided
@@ -74,7 +157,7 @@ command :new_story do |c|
74
157
  # entire story to be created.
75
158
  else
76
159
  if options[:i]
77
- project_id = KiPivotal::Interactive.select_project
160
+ project_id = KiPivotal::Interactive.select_project("Which project should this story be created under?")
78
161
  story_json = KiPivotal::Interactive.new_story
79
162
  else
80
163
  $stderr.puts "\n Input must be given to this tool to create a story."
data/ki_pivotal.gemspec CHANGED
@@ -15,16 +15,16 @@ Gem::Specification.new do |gem|
15
15
  gem.require_paths = ["lib"]
16
16
  gem.version = KiPivotal::VERSION
17
17
 
18
- gem.add_dependency 'gli'
19
- gem.add_dependency 'multi_json'
20
- gem.add_dependency 'pivotal-tracker'
21
- gem.add_dependency 'colored'
18
+ gem.add_dependency('gli', '~> 1.6.0')
19
+ gem.add_dependency('multi_json', '~> 1.3.6')
20
+ gem.add_dependency('pivotal-tracker', '~> 0.5.4')
21
+ gem.add_dependency('colored', '~> 1.2.0')
22
22
 
23
- gem.add_development_dependency('debugger')
24
- gem.add_development_dependency('rake')
25
- gem.add_development_dependency('simplecov')
26
- gem.add_development_dependency('rspec')
27
- gem.add_development_dependency('test-construct')
28
- gem.add_development_dependency('vcr')
29
- gem.add_development_dependency('webmock')
23
+ gem.add_development_dependency('debugger', '~> 1.2.0')
24
+ gem.add_development_dependency('rake', '~> 0.9.2')
25
+ gem.add_development_dependency('rspec', '~> 2.11.0')
26
+ gem.add_development_dependency('simplecov', '~> 0.6.4')
27
+ gem.add_development_dependency('test-construct', '~> 1.2.0')
28
+ gem.add_development_dependency('vcr', '~> 2.2.4')
29
+ gem.add_development_dependency('webmock', '~> 1.8.8')
30
30
  end
@@ -47,6 +47,30 @@ module KiPivotal
47
47
  end
48
48
  end
49
49
 
50
+ def stories_in_project(project_id, opts = {})
51
+ with_session do
52
+ pretty = opts.fetch(:pretty) { true }
53
+
54
+ project = PivotalTracker::Project.find(project_id)
55
+
56
+ data = project.stories.all.inject([]) { |array, story| array << story_to_hash(story).merge({'project_id' => project_id}) }
57
+
58
+ MultiJson.dump(data, :pretty => pretty)
59
+ end
60
+ end
61
+
62
+ def story_in_project(story_id, project_id, opts = {})
63
+ with_session do
64
+ pretty = opts.fetch(:pretty) { true }
65
+
66
+ project = PivotalTracker::Project.find(project_id)
67
+
68
+ data = story_to_hash(project.stories.find(story_id)).merge({'project_id' => project_id})
69
+
70
+ MultiJson.dump(data, :pretty => pretty)
71
+ end
72
+ end
73
+
50
74
  private
51
75
 
52
76
  # TODO - We need to determine what concerns the API has vs
@@ -69,18 +93,25 @@ module KiPivotal
69
93
  story = project.stories.create(data)
70
94
 
71
95
  if story.errors.empty?
72
- created_story = {}
73
- story.instance_variables.each do |instance_var|
74
- string_name = instance_var.to_s.gsub('@','')
75
- created_story[string_name] = story.instance_variable_get(instance_var)
76
- end
77
- created_story
96
+ story_to_hash(story)
78
97
  else
79
98
  all_errors = story.errors.errors.last
80
99
  raise ApiError, "JSON for story was invalid: #{all_errors}"
81
100
  end
82
101
  end
83
102
 
103
+ def story_to_hash(story)
104
+ {'ki_type' => 'pivotal_story',
105
+ 'id' => story.id,
106
+ 'name' => story.name,
107
+ 'story_type' => story.story_type,
108
+ 'estimate' => story.estimate,
109
+ 'story_url' => story.url,
110
+ 'description' => story.description,
111
+ 'requested_by' => story.requested_by,
112
+ 'current_state' => story.current_state}
113
+ end
114
+
84
115
  def from_and_to_json(json, pretty=false)
85
116
  data = MultiJson.load(json)
86
117
  new_data = yield data
@@ -36,16 +36,29 @@ module KiPivotal
36
36
  $stdin.gets.chomp
37
37
  end
38
38
 
39
- def self.select_project
39
+ def self.select_story(project_id, prompt)
40
+ stories = MultiJson.load(KiPivotal::Api.new.stories_in_project(project_id))
41
+
42
+ if stories.size > 1
43
+ index = repeatedly_choose_from(stories.map { |p| p['name'] }, prompt)
44
+ else
45
+ index = 0
46
+ end
47
+
48
+ $stderr.puts "\n Chosen story is '#{stories[index]['name']}'"
49
+ stories[index]['id']
50
+ end
51
+
52
+ def self.select_project(prompt)
40
53
  projects = MultiJson.load(KiPivotal::Api.new.projects)
41
54
 
42
55
  if projects.size > 1
43
- index = repeatedly_choose_from(projects.map { |p| p['name'] }, "Which project should this story be created under?")
56
+ index = repeatedly_choose_from(projects.map { |p| p['name'] }, prompt)
44
57
  else
45
58
  index = 0
46
59
  end
47
60
 
48
- $stderr.puts "\n Story will be created under the project, '#{projects[index]['name']}'"
61
+ $stderr.puts "\n Chosen project is '#{projects[index]['name']}'"
49
62
  projects[index]['id']
50
63
  end
51
64
 
@@ -1,3 +1,3 @@
1
1
  module KiPivotal
2
- VERSION = "0.0.3"
2
+ VERSION = "0.0.4"
3
3
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: ki_pivotal
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.3
4
+ version: 0.0.4
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -10,129 +10,129 @@ authors:
10
10
  autorequire:
11
11
  bindir: bin
12
12
  cert_chain: []
13
- date: 2012-08-15 00:00:00.000000000Z
13
+ date: 2012-08-16 00:00:00.000000000Z
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
16
  name: gli
17
- requirement: &70107004966400 !ruby/object:Gem::Requirement
17
+ requirement: &70289977107260 !ruby/object:Gem::Requirement
18
18
  none: false
19
19
  requirements:
20
- - - ! '>='
20
+ - - ~>
21
21
  - !ruby/object:Gem::Version
22
- version: '0'
22
+ version: 1.6.0
23
23
  type: :runtime
24
24
  prerelease: false
25
- version_requirements: *70107004966400
25
+ version_requirements: *70289977107260
26
26
  - !ruby/object:Gem::Dependency
27
27
  name: multi_json
28
- requirement: &70107004965980 !ruby/object:Gem::Requirement
28
+ requirement: &70289977106760 !ruby/object:Gem::Requirement
29
29
  none: false
30
30
  requirements:
31
- - - ! '>='
31
+ - - ~>
32
32
  - !ruby/object:Gem::Version
33
- version: '0'
33
+ version: 1.3.6
34
34
  type: :runtime
35
35
  prerelease: false
36
- version_requirements: *70107004965980
36
+ version_requirements: *70289977106760
37
37
  - !ruby/object:Gem::Dependency
38
38
  name: pivotal-tracker
39
- requirement: &70107004965560 !ruby/object:Gem::Requirement
39
+ requirement: &70289977106300 !ruby/object:Gem::Requirement
40
40
  none: false
41
41
  requirements:
42
- - - ! '>='
42
+ - - ~>
43
43
  - !ruby/object:Gem::Version
44
- version: '0'
44
+ version: 0.5.4
45
45
  type: :runtime
46
46
  prerelease: false
47
- version_requirements: *70107004965560
47
+ version_requirements: *70289977106300
48
48
  - !ruby/object:Gem::Dependency
49
49
  name: colored
50
- requirement: &70107004965140 !ruby/object:Gem::Requirement
50
+ requirement: &70289977105840 !ruby/object:Gem::Requirement
51
51
  none: false
52
52
  requirements:
53
- - - ! '>='
53
+ - - ~>
54
54
  - !ruby/object:Gem::Version
55
- version: '0'
55
+ version: 1.2.0
56
56
  type: :runtime
57
57
  prerelease: false
58
- version_requirements: *70107004965140
58
+ version_requirements: *70289977105840
59
59
  - !ruby/object:Gem::Dependency
60
60
  name: debugger
61
- requirement: &70107004994920 !ruby/object:Gem::Requirement
61
+ requirement: &70289977105380 !ruby/object:Gem::Requirement
62
62
  none: false
63
63
  requirements:
64
- - - ! '>='
64
+ - - ~>
65
65
  - !ruby/object:Gem::Version
66
- version: '0'
66
+ version: 1.2.0
67
67
  type: :development
68
68
  prerelease: false
69
- version_requirements: *70107004994920
69
+ version_requirements: *70289977105380
70
70
  - !ruby/object:Gem::Dependency
71
71
  name: rake
72
- requirement: &70107004994500 !ruby/object:Gem::Requirement
72
+ requirement: &70289977104920 !ruby/object:Gem::Requirement
73
73
  none: false
74
74
  requirements:
75
- - - ! '>='
75
+ - - ~>
76
76
  - !ruby/object:Gem::Version
77
- version: '0'
77
+ version: 0.9.2
78
78
  type: :development
79
79
  prerelease: false
80
- version_requirements: *70107004994500
80
+ version_requirements: *70289977104920
81
81
  - !ruby/object:Gem::Dependency
82
- name: simplecov
83
- requirement: &70107004994080 !ruby/object:Gem::Requirement
82
+ name: rspec
83
+ requirement: &70289977104460 !ruby/object:Gem::Requirement
84
84
  none: false
85
85
  requirements:
86
- - - ! '>='
86
+ - - ~>
87
87
  - !ruby/object:Gem::Version
88
- version: '0'
88
+ version: 2.11.0
89
89
  type: :development
90
90
  prerelease: false
91
- version_requirements: *70107004994080
91
+ version_requirements: *70289977104460
92
92
  - !ruby/object:Gem::Dependency
93
- name: rspec
94
- requirement: &70107004993660 !ruby/object:Gem::Requirement
93
+ name: simplecov
94
+ requirement: &70289977104000 !ruby/object:Gem::Requirement
95
95
  none: false
96
96
  requirements:
97
- - - ! '>='
97
+ - - ~>
98
98
  - !ruby/object:Gem::Version
99
- version: '0'
99
+ version: 0.6.4
100
100
  type: :development
101
101
  prerelease: false
102
- version_requirements: *70107004993660
102
+ version_requirements: *70289977104000
103
103
  - !ruby/object:Gem::Dependency
104
104
  name: test-construct
105
- requirement: &70107004993240 !ruby/object:Gem::Requirement
105
+ requirement: &70289977103540 !ruby/object:Gem::Requirement
106
106
  none: false
107
107
  requirements:
108
- - - ! '>='
108
+ - - ~>
109
109
  - !ruby/object:Gem::Version
110
- version: '0'
110
+ version: 1.2.0
111
111
  type: :development
112
112
  prerelease: false
113
- version_requirements: *70107004993240
113
+ version_requirements: *70289977103540
114
114
  - !ruby/object:Gem::Dependency
115
115
  name: vcr
116
- requirement: &70107004992820 !ruby/object:Gem::Requirement
116
+ requirement: &70289996128980 !ruby/object:Gem::Requirement
117
117
  none: false
118
118
  requirements:
119
- - - ! '>='
119
+ - - ~>
120
120
  - !ruby/object:Gem::Version
121
- version: '0'
121
+ version: 2.2.4
122
122
  type: :development
123
123
  prerelease: false
124
- version_requirements: *70107004992820
124
+ version_requirements: *70289996128980
125
125
  - !ruby/object:Gem::Dependency
126
126
  name: webmock
127
- requirement: &70107004992400 !ruby/object:Gem::Requirement
127
+ requirement: &70289996128520 !ruby/object:Gem::Requirement
128
128
  none: false
129
129
  requirements:
130
- - - ! '>='
130
+ - - ~>
131
131
  - !ruby/object:Gem::Version
132
- version: '0'
132
+ version: 1.8.8
133
133
  type: :development
134
134
  prerelease: false
135
- version_requirements: *70107004992400
135
+ version_requirements: *70289996128520
136
136
  description: Kiseru Pivotal Tracker client
137
137
  email:
138
138
  - ben@freeagent.com