westarete-tracker-tools 0.3.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.
data/.document ADDED
@@ -0,0 +1,5 @@
1
+ lib/**/*.rb
2
+ bin/*
3
+ -
4
+ features/**/*.feature
5
+ LICENSE.txt
data/.rspec ADDED
@@ -0,0 +1,2 @@
1
+ --format nested
2
+ --color
data/.rvmrc ADDED
@@ -0,0 +1 @@
1
+ rvm use 1.8.7@westarete-tracker-tools
data/Gemfile ADDED
@@ -0,0 +1,30 @@
1
+ source :rubygems
2
+
3
+ # Tools for creating a gem
4
+ gem 'jeweler', '1.5.2'
5
+
6
+ # API wrapper for Pivotal Tracker
7
+ gem 'pivotal-tracker', '0.3.0'
8
+
9
+ # Validations and relationships
10
+ gem 'activemodel', '3.0.3'
11
+
12
+ group :development do
13
+ # Test framework
14
+ gem 'rspec', '2.2.0'
15
+
16
+ # Produce rspec output in junit format for jenkins
17
+ gem 'ci_reporter', '1.6.4'
18
+
19
+ # Measure test coverage
20
+ gem 'rcov', '0.9.9'
21
+
22
+ # Automatically run tests as you code
23
+ gem 'autotest', '4.4.6'
24
+
25
+ # Record and play back API requests during tests
26
+ gem 'vcr', '1.4.0'
27
+
28
+ # Mock out API requests
29
+ gem 'fakeweb', '1.3.0'
30
+ end
data/Gemfile.lock ADDED
@@ -0,0 +1,59 @@
1
+ GEM
2
+ remote: http://rubygems.org/
3
+ specs:
4
+ ZenTest (4.4.2)
5
+ activemodel (3.0.3)
6
+ activesupport (= 3.0.3)
7
+ builder (~> 2.1.2)
8
+ i18n (~> 0.4)
9
+ activesupport (3.0.3)
10
+ autotest (4.4.6)
11
+ ZenTest (>= 4.4.1)
12
+ builder (2.1.2)
13
+ ci_reporter (1.6.4)
14
+ builder (>= 2.1.2)
15
+ diff-lcs (1.1.2)
16
+ fakeweb (1.3.0)
17
+ git (1.2.5)
18
+ happymapper (0.3.2)
19
+ libxml-ruby (~> 1.1.3)
20
+ i18n (0.5.0)
21
+ jeweler (1.5.2)
22
+ bundler (~> 1.0.0)
23
+ git (>= 1.2.5)
24
+ rake
25
+ libxml-ruby (1.1.4)
26
+ mime-types (1.16)
27
+ nokogiri (1.4.3.1)
28
+ pivotal-tracker (0.3.0)
29
+ builder
30
+ happymapper (>= 0.3.2)
31
+ nokogiri (~> 1.4.3.1)
32
+ rest-client (~> 1.6.0)
33
+ rake (0.8.7)
34
+ rcov (0.9.9)
35
+ rest-client (1.6.1)
36
+ mime-types (>= 1.16)
37
+ rspec (2.2.0)
38
+ rspec-core (~> 2.2)
39
+ rspec-expectations (~> 2.2)
40
+ rspec-mocks (~> 2.2)
41
+ rspec-core (2.4.0)
42
+ rspec-expectations (2.4.0)
43
+ diff-lcs (~> 1.1.2)
44
+ rspec-mocks (2.4.0)
45
+ vcr (1.4.0)
46
+
47
+ PLATFORMS
48
+ ruby
49
+
50
+ DEPENDENCIES
51
+ activemodel (= 3.0.3)
52
+ autotest (= 4.4.6)
53
+ ci_reporter (= 1.6.4)
54
+ fakeweb (= 1.3.0)
55
+ jeweler (= 1.5.2)
56
+ pivotal-tracker (= 0.3.0)
57
+ rcov (= 0.9.9)
58
+ rspec (= 2.2.0)
59
+ vcr (= 1.4.0)
data/LICENSE.txt ADDED
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2011 West Arete Computing, Inc.
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,190 @@
1
+ # westarete-tracker-tools
2
+
3
+ This gem contains a set of tools and extensions that West Arete uses to report
4
+ on [Pivotal Tracker](https://www.pivotaltracker.com/) across all of its
5
+ projects.
6
+
7
+ ## Goals
8
+
9
+ * Extract the set of stories that are available to work on across all active
10
+ projects
11
+ * Validate stories in the backlog to ensure that they meet our standards
12
+ * Report on completed iterations for billing and reporting purposes
13
+ * Wedge the following additional information into each feature:
14
+ * Risk
15
+ * Price
16
+
17
+ ## Manifesto
18
+
19
+ This is an opinionated gem. It assumes that you are using Tracker the way that
20
+ West Arete is using it. That is to say:
21
+
22
+ * Stories are not available to be worked on until they are in the backlog
23
+ * Features are not allowed into the backlog until they have all of the
24
+ following attributes:
25
+ * A substantial description
26
+ * A point estimate
27
+ * A risk rating (see below)
28
+ * A price or cost estimate (see below)
29
+ * Stories should be requested by the project's stakeholder
30
+ * Acceptance of a story implies that it is ready to be invoiced
31
+
32
+ If these rules do not hold true for your organization, you may need to fork
33
+ this project and modify the behavior so that it better suits your needs.
34
+
35
+ ### Risk
36
+
37
+ West Arete assigns an objective risk rating to each feature. This helps us to
38
+ achieve a balanced risk profile for each iteration for the sake of developer
39
+ productivity and happiness. It also gives valuable feedback to the managers
40
+ about how the feature should be priced, so that risk is apportioned fairly
41
+ between West Arete and the client.
42
+
43
+ Our ratings borrow from the rock climbing tradition of using movie ratings
44
+ to communicate risk. A climb that is rated PG is generally less dangerous than
45
+ one that is rated R. In the same way, we assign a risk rating to each feature:
46
+
47
+ * G: I have implemented something exactly like this recently.
48
+ * PG: I have implemented something quite similar to this.
49
+ * PG-13: I know how to do this, but it will involve a gem, library, or
50
+ technique that I haven't used before.
51
+ * R: I know how to do this, but I don't know exactly how long it will take; or
52
+ it involves an entirely new environment; or it involves adopting outsiders'
53
+ code.
54
+ * X: I'm not completely sure I will succeed at implementing this.
55
+
56
+ Risk ratings are only assigned to features. They are not assigned to bugs,
57
+ chores, or releases (although an average rating could probably be determined
58
+ for the latter).
59
+
60
+ There are a couple implicit ramifications of this system:
61
+
62
+ * Risk is dependent upon the person or team who will be implementing the
63
+ feature -- what is G for one person or team may be R for another.
64
+ * Risk is dependent upon the implementation. The decision to implement a
65
+ feature using a new gem will increase the risk to at least PG-13, even if it's
66
+ anticipated that it will be easier to accomplish (which may reduce the point
67
+ estimate).
68
+
69
+ Risk is encoded into a story in Tracker by enclosing it in square braces at
70
+ the beginning of the feature's title. For example:
71
+
72
+ [PG-13] Geolocation
73
+
74
+ ### Price
75
+
76
+ West Arete generally prices its services per feature. Whenever possible, the
77
+ price is set as a fixed bid per story. However, when the risk for a feature is
78
+ too high, the feature is usually implemented at an hourly rate so that the
79
+ risk is shared by both West Arete and the Client.
80
+
81
+ With this library, prices are set in Tracker by having a manager comment on
82
+ the story with the estimated price. The library picks up on this by searching
83
+ the managers' comments for the words "cost" or "price" followed by a dollar
84
+ figure. The most recent managers' comment that sets a price wins.
85
+
86
+ ## Setup
87
+
88
+ You'll need to create a `.pivotal_tracker_api_token` file in your home
89
+ directory. It should contain nothing but your API key from the bottom of [your
90
+ Tracker profile page](https://www.pivotaltracker.com/profile).
91
+
92
+ ## Library
93
+
94
+ This gem provides a clean, high-level reporting interface to the [Pivotal
95
+ Tracker v3 API](https://www.pivotaltracker.com/help/api).
96
+
97
+ Under the covers, this gem uses the [pivotal-tracker
98
+ gem](https://github.com/jsmestad/pivotal-tracker) to do the actual
99
+ communication with the Pivotal API. We've encapsulated that gem's object model
100
+ to provide a higher level interface that adds our own custom functionality.
101
+
102
+ However, our interface is not a superset of the pivotal-tracker gem -- we've
103
+ only implemented the portions of the API that are useful to us.
104
+
105
+ The API documentation for this gem is here:
106
+
107
+ <http://rdoc.info/github/westarete/westarete-tracker-tools/master/frames>
108
+
109
+ ## Executables
110
+
111
+ There are two command-line executables that are included with the gem. They
112
+ build upon the library to do some key reporting for us.
113
+
114
+ Both scripts presume that they're being run on Mac OS X, so that they can
115
+ easily write to the clipboard.
116
+
117
+ ### backlog
118
+
119
+ This script collects all stories that are available to be worked on across
120
+ all projects.
121
+
122
+ Example usage:
123
+
124
+ bundle exec bin/backlog
125
+
126
+ The standard output reports progress and any story validation errors that are
127
+ encountered. A healthy backlog should have no errors. A link to each story
128
+ is provided.
129
+
130
+ After the script has completed successfully, a report of all the available
131
+ stories is copied to the clipboard and is ready to be pasted into a
132
+ spreadsheet.
133
+
134
+ ### done
135
+
136
+ This script summarizes the accepted stories across all projects for a given
137
+ iteration.
138
+
139
+ It accepts a sole command line argument: an integer of zero or less, which
140
+ represents the iteration offset. An offset of zero means the current
141
+ iteration. An offset of -1 means the previous iteration. An offset of -2 means
142
+ two iterations ago, etc. If the script is run with no arguments, it reports on
143
+ the current iteration (an offset of 0).
144
+
145
+ Example usage:
146
+
147
+ bundle exec bin/done -2
148
+
149
+ This will gather all completed stories from two iterations ago. The standard
150
+ output will report on progress and any invalid stories that are encountered.
151
+ After completion, a summary of the stories will be left on the clipboard,
152
+ ready to be pasted into a spreadsheet.
153
+
154
+ ### finished
155
+
156
+ This script looks for stories that are close to being done. They may be in a
157
+ state of "finished", "delivered", or "rejected". The team can run this
158
+ periodically to see which stories or stakeholders need a nudge to get a story
159
+ completed.
160
+
161
+ ### validate
162
+
163
+ This script simply scrutinizes the backlog looking for stories that fail
164
+ validation. It reports any problems and then exits with a non-zero status if
165
+ any stories fail. It's designed to be run from a continuous integration
166
+ system.
167
+
168
+ ## Contributing to westarete-tracker-tools
169
+
170
+ * Check out the latest master to make sure the feature hasn't been implemented
171
+ or the bug hasn't been fixed yet
172
+ * Check out the issue tracker to make sure someone already hasn't requested it
173
+ and/or contributed it
174
+ * Fork the project
175
+ * Start a feature/bugfix branch
176
+ * Commit and push until you are happy with your contribution
177
+ * Make sure to add tests for it. This is important so I don't break it in a
178
+ future version unintentionally.
179
+ * Please try not to mess with the Rakefile, version, or history. If you want
180
+ to have your own version, or is otherwise necessary, that is fine, but please
181
+ isolate to its own commit so I can cherry-pick around it.
182
+
183
+ This project follows the conventions of [Semantic
184
+ Versioning](http://semver.org/).
185
+
186
+ ## Copyright
187
+
188
+ Copyright (c) 2011 West Arete Computing, Inc. See LICENSE.txt for
189
+ further details.
190
+
data/Rakefile ADDED
@@ -0,0 +1,79 @@
1
+ require 'rubygems'
2
+ require 'bundler'
3
+ begin
4
+ Bundler.setup(:default, :development)
5
+ rescue Bundler::BundlerError => e
6
+ $stderr.puts e.message
7
+ $stderr.puts "Run `bundle install` to install missing gems"
8
+ exit e.status_code
9
+ end
10
+ require 'rake'
11
+
12
+ require 'jeweler'
13
+ Jeweler::Tasks.new do |gem|
14
+ # gem is a Gem::Specification... see http://docs.rubygems.org/read/chapter/20 for more options
15
+ gem.name = "westarete-tracker-tools"
16
+ gem.homepage = "http://github.com/westarete/westarete-tracker-tools"
17
+ gem.license = "MIT"
18
+ gem.summary = %Q{A set of tools and extensions that West Arete uses to report
19
+ on Pivotal Tracker.}
20
+ gem.description = %Q{
21
+ This gem contains a set of tools and extensions that West Arete uses to report
22
+ on Pivotal Tracker across all of its projects.
23
+
24
+ Goals:
25
+
26
+ * Extract the set of stories that are available to work on across all active
27
+ projects
28
+ * Validate stories in the backlog to ensure that they meet our standards
29
+ * Report on completed iterations for billing and reporting purposes
30
+ * Wedge the following additional information into each feature:
31
+ * Risk
32
+ * Price
33
+ }
34
+ gem.email = "scott@westarete.com"
35
+ gem.authors = ["Scott Woods"]
36
+ # Include your dependencies below. Runtime dependencies are required when using your gem,
37
+ # and development dependencies are only needed for development (ie running rake tasks, tests, etc)
38
+ # gem.add_runtime_dependency 'jabber4r', '> 0.1'
39
+ # gem.add_development_dependency 'rspec', '> 1.2.3'
40
+ end
41
+ Jeweler::RubygemsDotOrgTasks.new
42
+
43
+ # Produce test output that jenkins can read.
44
+ require 'ci/reporter/rake/rspec' # use this if you're using RSpec
45
+ # require 'ci/reporter/rake/cucumber' # use this if you're using Cucumber
46
+ # require 'ci/reporter/rake/test_unit' # use this if you're using Test::Unit
47
+
48
+ begin
49
+ require 'rspec/core/rake_task'
50
+ RSpec::Core::RakeTask.new('spec')
51
+ RSpec::Core::RakeTask.new('spec:rcov') do |t|
52
+ t.rcov = true
53
+ t.rcov_opts = %w{ --exclude spec --exclude gems }
54
+ end
55
+ task :default => :spec
56
+ rescue LoadError
57
+ puts "Could not find rspec gem. RSpec tasks will not be available."
58
+ end
59
+
60
+ begin
61
+ require 'rcov/rcovtask'
62
+ Rcov::RcovTask.new do |test|
63
+ test.libs << 'spec'
64
+ test.pattern = 'spec/**/*_spec.rb'
65
+ test.verbose = true
66
+ end
67
+ rescue LoadError
68
+ puts "Could not find rcov gem. Coverage tasks will not be available."
69
+ end
70
+
71
+ require 'rake/rdoctask'
72
+ Rake::RDocTask.new do |rdoc|
73
+ version = File.exist?('VERSION') ? File.read('VERSION') : ""
74
+
75
+ rdoc.rdoc_dir = 'rdoc'
76
+ rdoc.title = "westarete-tracker-tools #{version}"
77
+ rdoc.rdoc_files.include('README*')
78
+ rdoc.rdoc_files.include('lib/**/*.rb')
79
+ end
data/VERSION ADDED
@@ -0,0 +1 @@
1
+ 0.3.0
@@ -0,0 +1 @@
1
+ Autotest.add_discovery { "rspec2" }
data/bin/backlog ADDED
@@ -0,0 +1,47 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ # Extract all stories across all backlogs of all projects into a format
4
+ # that's ready to be pasted into a spreadsheet. Also report on any validation
5
+ # errors that are encountered.
6
+
7
+ require 'rubygems'
8
+ require 'bundler/setup'
9
+ $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
10
+ require 'westarete-tracker-tools'
11
+
12
+ include WestAreteTrackerTools
13
+
14
+ number_of_problems = 0
15
+ IO.popen('pbcopy', 'w') do |clipboard|
16
+ Project.all.each do |project|
17
+ puts "- #{project.name}"
18
+ project.backlog.each do |story|
19
+ if ! story.valid?
20
+ puts " - Invalid Story"
21
+ puts " story_type: #{story.story_type}"
22
+ puts " name: \"#{story.name}\""
23
+ puts " url: #{story.url}"
24
+ puts " errors:"
25
+ story.errors.full_messages.each do |error|
26
+ puts " - #{error}"
27
+ end
28
+ number_of_problems += 1
29
+ end
30
+ clipboard.puts [
31
+ nil, # week starting
32
+ project.name,
33
+ story.story_type,
34
+ story.points,
35
+ story.risk,
36
+ nil, # deliverable type
37
+ story.name,
38
+ nil, # fixed / hourly
39
+ story.price,
40
+ story.url
41
+ ].join("\t")
42
+ end
43
+ end
44
+ end
45
+ puts "\nDone."
46
+ puts "The master backlog has been copied to your clipboard and is ready to be pasted into a spreadsheet."
47
+ exit number_of_problems