crab 0.1.6 → 0.1.7

Sign up to get free protection for your applications and to get access to all the features.
data/README.md CHANGED
@@ -139,25 +139,36 @@ If you have any problems, please let us know.
139
139
  [4]: http://gembundler.com
140
140
  [5]: https://github.com/cucumber/aruba
141
141
 
142
- To do
143
- -----
142
+ To do / Roadmap
143
+ ---------------
144
144
 
145
- - Add a config command + .crab/config file to hold settings like project, etc
146
- - Add a `push` subcommand which parses a Cucumber feature and adds or updates it in Rally
145
+ ### 0.2.0
146
+
147
+ - Add a `move` subcommand which moves the story from one state to the next (potentially, `move --back`)
147
148
  - `pull` is not very smart and could detect feature files being moved from one dir to another
148
149
  - Recursively look for a `.crab` directory like Git does with `.git`
149
- - Encrypt password in generated `~/.crab/credentials`
150
150
  - Verbose logging (especially before any change or destructive operations in Rally)
151
- - Dry-run mode
152
151
  - Figure out how to stub or simulate Rally (tests are taking way too long already)
152
+
153
+ ### 0.3.0
154
+
155
+ - Add a `push` subcommand which parses a Cucumber feature and adds or updates it in Rally
156
+ - Add a config command + .crab/config file to hold settings like project, etc
153
157
  - Error messages are still more cryptic than we'd like
154
- - Add a `move` subcommand which moves the story from one state to the next (potentially, `move --back`)
155
- - Add a Cucumber Formatter that updates Test Runs in Rally with results from CI
156
- - Investigate use of other fields like Priority and Risk in Rally Test Cases
157
158
  - Make it possible to associate defects with Features (essentially treating defects like stories)
158
- - Test in Ruby 1.9
159
159
  - Use the Gherkin models and formatters instead of dumb string templates to generate feature files
160
160
 
161
+ ### Later / before 1.0.0
162
+
163
+ - Dry-run mode
164
+ - Encrypt password in generated `~/.crab/credentials`
165
+ - Add a Cucumber Formatter that updates Test Runs in Rally with results from CI
166
+ - Test in Ruby 1.9
167
+
168
+ ### After 1.0.0
169
+
170
+ - Bash completion scripts
171
+
161
172
  Suggestions? Please get in touch!
162
173
 
163
174
  Authors and Contributors
@@ -1,10 +1,10 @@
1
1
  Feature: Show Story From Rally
2
-
2
+
3
3
  In order to see what's in a story
4
4
  A lazy developer
5
5
  Wants to be able to do it from the command line
6
6
 
7
- Background:
7
+ Background:
8
8
  Given I am logged in
9
9
 
10
10
  Scenario: Show Simple Story
@@ -19,7 +19,7 @@ Feature: Show Story From Rally
19
19
  Scenario: Show Story With Test Cases
20
20
  When I run `crab show US5000`
21
21
  Then the output should contain "Feature: [US5000] Sample Crab Parent Story"
22
- And the output should contain "@manual @functional"
22
+ And the output should contain "@important @medium @manual @acceptance"
23
23
  And the output should contain "Scenario: [TC10388] Sample Testcase"
24
24
  And the output should contain " Given Rally behaves"
25
25
  And the output should contain " When I look at the test case steps"
@@ -11,15 +11,16 @@ Feature: Subcommand Help
11
11
 
12
12
  Scenario: Help
13
13
  When I run `crab -h`
14
- Then the output should contain " create Create a new story in Rally"
15
- Then the output should contain " delete Delete an existing story in Rally"
16
- And the output should contain " find Find stories by text in name, description or notes"
17
- And the output should contain " login Persistently authenticate user with Rally"
18
- And the output should contain " project Persistently select project to work with in Rally"
19
- And the output should contain " pull Downloads stories (and its test cases) as Cucumber feature files"
20
- And the output should contain " show Show a story (and its test cases) as a Cucumber feature"
21
- And the output should contain " testcase Manage test cases in a story (add, update, delete)"
22
- And the output should contain " update Update a story (name, estimate, etc)"
14
+ Then the output should contain "create Create a new story in Rally"
15
+ And the output should contain "delete Delete an existing story in Rally"
16
+ And the output should contain "find Find stories by text in name, description or notes"
17
+ And the output should contain "login Persistently authenticate user with Rally"
18
+ And the output should contain "move Move a story from one status to the next (or previous)"
19
+ And the output should contain "project Persistently select project to work with in Rally"
20
+ And the output should contain "pull Downloads stories (and its test cases) as Cucumber feature files"
21
+ And the output should contain "show Show a story (and its test cases) as a Cucumber feature"
22
+ And the output should contain "testcase Manage test cases in a story (add, update, delete)"
23
+ And the output should contain "update Update a story (name, estimate, etc)"
23
24
 
24
25
  Scenario: Bogus Subcommand
25
26
  When I run `crab bogus`
@@ -97,3 +98,12 @@ Feature: Subcommand Help
97
98
  Usage: crab [options] find [options] [text]
98
99
  """
99
100
 
101
+ Scenario: Move Subcommand
102
+ When I run `crab move --help`
103
+ Then the output should contain:
104
+ """
105
+ crab move: move a story from one status to the next (or previous)
106
+
107
+ Usage: crab [options] move story [options]
108
+ """
109
+
@@ -1,32 +1,32 @@
1
1
  require "crab/version"
2
2
 
3
3
  # common dependencies
4
- require 'trollop'
4
+ require 'active_support/all'
5
5
  require 'fileutils'
6
6
  require 'gherkin/i18n'
7
7
  require 'highline/import'
8
- require 'active_support/all'
9
8
  require 'rally_rest_api'
10
9
  require 'sanitize'
10
+ require 'trollop'
11
11
 
12
12
  # internals
13
13
  require "crab/utilities"
14
+ require "crab/cli"
14
15
  require "crab/rally"
15
16
  require "crab/story"
16
17
  require "crab/testcase"
17
- require "crab/cli"
18
- require "crab/scenario"
19
18
 
20
19
  # supported commands
21
- require "crab/commands/update"
22
- require "crab/commands/pull"
20
+ require "crab/commands/create"
21
+ require "crab/commands/delete"
23
22
  require "crab/commands/find"
24
23
  require "crab/commands/login"
25
- require "crab/commands/show"
24
+ require "crab/commands/move"
26
25
  require "crab/commands/project"
27
- require "crab/commands/create"
28
- require "crab/commands/delete"
26
+ require "crab/commands/pull"
27
+ require "crab/commands/show"
29
28
  require "crab/commands/testcase"
29
+ require "crab/commands/update"
30
30
 
31
31
  # cucumber support
32
32
  require "crab/cucumber_feature"
@@ -1,6 +1,17 @@
1
1
  module Crab
2
2
 
3
- SUB_COMMANDS = %w(pull login list update show find project create delete testcase)
3
+ SUB_COMMANDS = {
4
+ "create" => "Create a new story in Rally",
5
+ "delete" => "Delete an existing story in Rally",
6
+ "find" => "Find stories by text in name, description or notes",
7
+ "login" => "Persistently authenticate user with Rally",
8
+ "project" => "Persistently select project to work with in Rally",
9
+ "pull" => "Downloads stories (and its test cases) as Cucumber feature files",
10
+ "show" => "Show a story (and its test cases) as a Cucumber feature",
11
+ "testcase" => "Manage test cases in a story (add, update, delete)",
12
+ "update" => "Update a story (name, estimate, etc)",
13
+ "move" => "Move a story from one status to the next (or previous)",
14
+ }
4
15
 
5
16
  class CLI
6
17
  def self.start
@@ -9,17 +20,9 @@ module Crab
9
20
  banner """
10
21
  crab version #{Crab::VERSION}: A Cucumber-Rally bridge
11
22
 
12
- create Create a new story in Rally
13
- delete Delete an existing story in Rally
14
- find Find stories by text in name, description or notes
15
- login Persistently authenticate user with Rally
16
- project Persistently select project to work with in Rally
17
- pull Downloads stories (and its test cases) as Cucumber feature files
18
- show Show a story (and its test cases) as a Cucumber feature
19
- testcase Manage test cases in a story (add, update, delete)
20
- update Update a story (name, estimate, etc)
23
+ #{SUB_COMMANDS.keys.sort.map {|k| sprintf "%10s %s\n", k, SUB_COMMANDS[k] }.join}
21
24
  """
22
- stop_on SUB_COMMANDS
25
+ stop_on SUB_COMMANDS.keys
23
26
  end
24
27
 
25
28
  cmd = ARGV.shift # get the subcommand
@@ -0,0 +1,46 @@
1
+ module Crab::Commands
2
+
3
+ class Move
4
+
5
+ include Crab::Utilities
6
+
7
+ def initialize(global_opts, args)
8
+ @global_opts = global_opts
9
+ @args = args
10
+
11
+ @cmd_opts = Trollop::options do
12
+ banner "crab move: move a story from one status to the next (or previous)
13
+
14
+ Usage: crab [options] move story [options]"
15
+ opt :back, "Move story backwards (from accepted to completed, for example)"
16
+ end
17
+
18
+ @rally = Crab::Rally.new
19
+ end
20
+
21
+ def run
22
+ story_id = @args.join(" ")
23
+ Trollop::die "No story given" if story_id.empty?
24
+
25
+ @rally.connect
26
+
27
+ story = @rally.find_story_with_id story_id
28
+ state = state_from(story.state)
29
+
30
+ story.update :schedule_state => (@cmd_opts[:back] ? state_before(state) : state_after(state))
31
+
32
+ puts "#{story.formatted_id}: #{story.name} (#{story.state})"
33
+ end
34
+
35
+ def state_before(state)
36
+ i = (Crab::Story::VALID_STATES.index(state) || 0) - 1
37
+ Crab::Story::VALID_STATES[i < 0 ? 0 : i]
38
+ end
39
+
40
+ def state_after(state)
41
+ i = (Crab::Story::VALID_STATES.index(state) || 0) + 1
42
+ max = Crab::Story::VALID_STATES.size
43
+ Crab::Story::VALID_STATES[i >= max ? max -1 : i]
44
+ end
45
+ end
46
+ end
@@ -76,7 +76,7 @@ Usage: crab [options] testcase add story name [options]
76
76
  @rally.connect
77
77
  tc = @rally.find_test_case(tc_id)
78
78
  tc.update(sanitize_options(opts))
79
- puts "#{tc.story.formatted_id}/#{tc.formatted_id}: #{tc.name} (#{tc.tags.join(" ")}"
79
+ puts "#{tc.story.formatted_id}/#{tc.formatted_id}: #{tc.name} (#{tc.tags.join(" ")})"
80
80
  end
81
81
 
82
82
  def delete(tc_id)
@@ -2,6 +2,8 @@ module Crab::Commands
2
2
 
3
3
  class Update
4
4
 
5
+ include Crab::Utilities
6
+
5
7
  def initialize(global_opts, args)
6
8
  @global_opts = global_opts
7
9
  @args = args
@@ -74,10 +76,5 @@ Usage: crab [options] update story [options]"
74
76
  opts
75
77
  end
76
78
 
77
- def state_from(option)
78
- fixed_option = option.gsub(/(^\w|[-_]\w)/) { $1.upcase.gsub(/_/, '-') }
79
- Trollop::die :state, "has an invalid value" unless Crab::Story::VALID_STATES.include? fixed_option
80
- fixed_option
81
- end
82
79
  end
83
80
  end
@@ -6,10 +6,9 @@ module Crab
6
6
  end
7
7
 
8
8
  def generate_from(scenario)
9
- tags = [scenario.method, scenario.test_type]
10
9
  return <<-SCENARIO
11
10
 
12
- #{tags.map {|t| " @" + t.strip }.join}
11
+ #{scenario.tags.map {|tag| "@" + tag }.join(" ")}
13
12
  #{@language.keywords('scenario').last}: [#{scenario.formatted_id}] #{scenario.name}
14
13
  #{scenario.steps.join("\n ")}
15
14
  SCENARIO
@@ -1,7 +1,7 @@
1
1
  module Crab
2
2
  class Rally
3
3
 
4
- include Utilities
4
+ include Crab::Utilities
5
5
 
6
6
  def connect
7
7
  get_credentials
@@ -37,7 +37,7 @@ module Crab
37
37
  end
38
38
 
39
39
  def scenarios
40
- Array(@rally_story.test_cases).map {|tc| Scenario.new tc }
40
+ Array(@rally_story.test_cases).map {|tc| Crab::TestCase.new tc }
41
41
  end
42
42
 
43
43
  def update(opts)
@@ -51,5 +51,9 @@ module Crab
51
51
  @rally_test_case.update options
52
52
  end
53
53
 
54
+ def steps
55
+ Array(@rally_test_case.steps).map {|step| step.input }
56
+ end
57
+
54
58
  end
55
59
  end
@@ -1,5 +1,6 @@
1
1
  module Crab
2
2
  module Utilities
3
+
3
4
  def credentials_file
4
5
  FileUtils.mkdir_p File.expand_path("~/.crab")
5
6
  File.expand_path("~/.crab/credentials")
@@ -15,5 +16,12 @@ module Crab
15
16
  Trollop::die :project, "must be specified" if project_name.blank?
16
17
  project_name
17
18
  end
19
+
20
+ def state_from(option)
21
+ fixed_option = option.gsub(/(^\w|[-_]\w)/) { $1.upcase.gsub(/_/, '-') }
22
+ Trollop::die :state, "has an invalid value" unless Crab::Story::VALID_STATES.include? fixed_option
23
+ fixed_option
24
+ end
25
+
18
26
  end
19
27
  end
@@ -1,3 +1,3 @@
1
1
  module Crab
2
- VERSION = "0.1.6"
2
+ VERSION = "0.1.7"
3
3
  end
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: crab
3
3
  version: !ruby/object:Gem::Version
4
- hash: 23
4
+ hash: 21
5
5
  prerelease:
6
6
  segments:
7
7
  - 0
8
8
  - 1
9
- - 6
10
- version: 0.1.6
9
+ - 7
10
+ version: 0.1.7
11
11
  platform: ruby
12
12
  authors:
13
13
  - Carlos Villela
@@ -15,7 +15,7 @@ autorequire:
15
15
  bindir: bin
16
16
  cert_chain: []
17
17
 
18
- date: 2011-09-27 00:00:00 -03:00
18
+ date: 2011-09-28 00:00:00 -03:00
19
19
  default_executable:
20
20
  dependencies:
21
21
  - !ruby/object:Gem::Dependency
@@ -177,6 +177,7 @@ files:
177
177
  - lib/crab/commands/delete.rb
178
178
  - lib/crab/commands/find.rb
179
179
  - lib/crab/commands/login.rb
180
+ - lib/crab/commands/move.rb
180
181
  - lib/crab/commands/project.rb
181
182
  - lib/crab/commands/pull.rb
182
183
  - lib/crab/commands/show.rb
@@ -185,7 +186,6 @@ files:
185
186
  - lib/crab/cucumber_feature.rb
186
187
  - lib/crab/cucumber_scenario.rb
187
188
  - lib/crab/rally.rb
188
- - lib/crab/scenario.rb
189
189
  - lib/crab/story.rb
190
190
  - lib/crab/testcase.rb
191
191
  - lib/crab/utilities.rb
@@ -1,30 +0,0 @@
1
- module Crab
2
-
3
- class Scenario
4
-
5
- def initialize(rally_test_case)
6
- @rally_test_case = rally_test_case
7
- end
8
-
9
- def formatted_id
10
- @rally_test_case.formatted_i_d
11
- end
12
-
13
- def name
14
- @rally_test_case.name
15
- end
16
-
17
- def steps
18
- Array(@rally_test_case.steps).map {|step| step.input }
19
- end
20
-
21
- def method
22
- @rally_test_case.elements[:method].parameterize
23
- end
24
-
25
- def test_type
26
- @rally_test_case.elements[:type].parameterize
27
- end
28
- end
29
-
30
- end