assisted_workflow 0.1.4 → 0.2.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/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- assisted_workflow (0.1.4)
4
+ assisted_workflow (0.2.0)
5
5
  hashie (~> 2.0.5)
6
6
  octokit (~> 2.0)
7
7
  pivotal-tracker (~> 0.5.12)
@@ -2,8 +2,12 @@ require "assisted_workflow/version"
2
2
  require "assisted_workflow/exceptions"
3
3
 
4
4
  module AssistedWorkflow
5
- autoload :Pivotal, "assisted_workflow/pivotal"
6
- autoload :Git, "assisted_workflow/git"
7
- autoload :Github, "assisted_workflow/github"
8
5
  autoload :ConfigFile, "assisted_workflow/config_file"
6
+ autoload :Output, "assisted_workflow/output"
7
+
8
+ module Addons
9
+ autoload :Pivotal, "assisted_workflow/addons/pivotal"
10
+ autoload :Git, "assisted_workflow/addons/git"
11
+ autoload :Github, "assisted_workflow/addons/github"
12
+ end
9
13
  end
@@ -0,0 +1,46 @@
1
+ module AssistedWorkflow::Addons
2
+
3
+ class Base
4
+
5
+ def initialize(output, options = {})
6
+ @output = output
7
+ validate_options!(options)
8
+ end
9
+
10
+ def name
11
+ self.class.name.downcase.split("::").last
12
+ end
13
+
14
+ def valid?
15
+ false
16
+ end
17
+
18
+ class << self
19
+
20
+ def required_options(*args)
21
+ @required_options = Array(args).map(&:to_s)
22
+ end
23
+
24
+ def get_required_options
25
+ @required_options || []
26
+ end
27
+ end
28
+
29
+ protected #===============================================================
30
+
31
+ def log(message)
32
+ @output.say_status(name, message) if @output
33
+ end
34
+
35
+ def validate_options!(options)
36
+ if options.nil?
37
+ raise AssistedWorkflow::Error, "#{name} missing configuration"
38
+ end
39
+ missing_keys = self.class.get_required_options - options.keys
40
+ if missing_keys.size > 0
41
+ raise AssistedWorkflow::Error, "#{name} missing configuration: #{missing_keys.inspect}"
42
+ end
43
+ end
44
+
45
+ end
46
+ end
@@ -0,0 +1,108 @@
1
+ require "assisted_workflow/exceptions"
2
+ require "assisted_workflow/addons/base"
3
+
4
+ module AssistedWorkflow::Addons
5
+
6
+ class GitError < AssistedWorkflow::Error; end
7
+
8
+ class Git < Base
9
+
10
+ DESCRIPTION_LIMIT = 30
11
+
12
+ def initialize(output, options = {})
13
+ super
14
+ @command_options = {:raise_error => true}.merge(options)
15
+ end
16
+
17
+ # creates a new git branch based on story attributes
18
+ # the branch name format is:
19
+ # => story_onwer_username.story_id.story_name
20
+ def create_story_branch(story)
21
+ log "creating the feature branch"
22
+ branch = branch_name(story)
23
+ git "checkout -b #{branch}"
24
+ # git "push --set-upstream origin #{branch}"
25
+ end
26
+
27
+ # run all the git steps required for a clean pull request
28
+ def rebase_and_push
29
+ check_everything_commited!
30
+ branch = current_branch
31
+ git "checkout master"
32
+ git "pull --rebase"
33
+ git "checkout #{branch}"
34
+ git "rebase master"
35
+ git "push -u -f origin #{branch}"
36
+ end
37
+
38
+ # returns the current story id based on branch name
39
+ def current_story_id
40
+ current_branch.split(".")[1]
41
+ end
42
+
43
+ # returns the current local branch name
44
+ def current_branch
45
+ git("rev-parse --abbrev-ref HEAD", :silent => true)
46
+ end
47
+
48
+ # returns the repository name assigned to origin following the format:
49
+ # owner/project
50
+ def repository
51
+ url = git("config --get remote.origin.url", :error => "cannot find 'origin' remote repository url")
52
+ url.gsub("git@github.com:", "").gsub("https://github.com/", "").gsub(/\.git$/, "").chomp
53
+ end
54
+
55
+ # check if current branch is merged into master
56
+ def is_merged?
57
+ check_everything_commited!
58
+ branch = current_branch
59
+ git "checkout master"
60
+ git "pull --rebase"
61
+ merged = git("branch --merged").include?(branch)
62
+ git "checkout #{branch}"
63
+ merged
64
+ end
65
+
66
+ # removes current branch and its remote version
67
+ def remove_branch
68
+ branch = current_branch
69
+ git "push origin :#{branch}", :raise_error => false
70
+ git "checkout master"
71
+ git "branch -D #{branch}"
72
+ end
73
+
74
+ private #=================================================================
75
+
76
+ def git(command, options = {})
77
+ options = @command_options.merge(options)
78
+ puts "git #{command}" unless options[:silent] == true
79
+ result = system("git #{command}")
80
+ if system_error? && options[:raise_error]
81
+ msg = ["git command error", options[:error]].compact.join(": ")
82
+ raise GitError, msg
83
+ end
84
+ result
85
+ end
86
+
87
+ def system(command)
88
+ %x{#{command}}.chomp
89
+ end
90
+
91
+ def system_error?
92
+ $? != 0
93
+ end
94
+
95
+ def branch_name(story)
96
+ description = story.name.to_s.downcase.gsub(/\W/, "_").slice(0, DESCRIPTION_LIMIT)
97
+ [story.other_id, story.id, description].join(".").downcase
98
+ end
99
+
100
+ def not_commited_changes
101
+ git("status --porcelain", :silent => true).split("\n")
102
+ end
103
+
104
+ def check_everything_commited!
105
+ raise AssistedWorkflow::Error, "git: there are not commited changes" unless not_commited_changes.empty?
106
+ end
107
+ end
108
+ end
@@ -1,11 +1,14 @@
1
1
  require "assisted_workflow/exceptions"
2
+ require "assisted_workflow/addons/base"
2
3
  require "octokit"
3
4
 
4
- module AssistedWorkflow
5
+ module AssistedWorkflow::Addons
5
6
 
6
- class Github
7
- def initialize(options)
8
- validate_options!(options)
7
+ class Github < Base
8
+ required_options :token
9
+
10
+ def initialize(output, options = {})
11
+ super
9
12
  @client = Octokit::Client.new(:access_token => options["token"])
10
13
  end
11
14
 
@@ -16,31 +19,21 @@ module AssistedWorkflow
16
19
  # @param story [Story] Pivotal story object
17
20
  # @return [Sawyer::Resource] The newly created pull request
18
21
  def create_pull_request(repo, branch, story)
22
+ log "submiting the new pull request"
19
23
  base = "master"
20
24
  title = "[##{story.id}] #{story.name}"
21
25
  pull_request = @client.create_pull_request(repo, base, branch, title, story.description)
22
26
  if pull_request.nil?
23
27
  raise AssistedWorkflow::Error, "error on submiting the pull request"
24
28
  else
25
- pull_request
29
+ url = pull_request._links.html.href
30
+ log "new pull request at #{url}"
31
+ url
26
32
  end
27
33
  end
28
34
 
29
35
  def valid?
30
36
  @client.user_authenticated?
31
37
  end
32
-
33
- private
34
-
35
- def validate_options!(options)
36
- if options.nil? || options.empty?
37
- raise AssistedWorkflow::Error, "github missing configuration"
38
- end
39
- required_keys = %w(token)
40
- missing_keys = required_keys - options.keys
41
- if missing_keys.size > 0
42
- raise AssistedWorkflow::Error, "github missing configuration: #{missing_keys.inspect}"
43
- end
44
- end
45
38
  end
46
39
  end
@@ -1,12 +1,14 @@
1
1
  require "assisted_workflow/exceptions"
2
+ require "assisted_workflow/addons/base"
2
3
  require 'pivotal_tracker'
3
4
 
4
5
  # wrapper class to pivotal api client
5
- module AssistedWorkflow
6
- class Pivotal
6
+ module AssistedWorkflow::Addons
7
+ class Pivotal < Base
8
+ required_options :fullname, :token, :project_id
7
9
 
8
- def initialize(options)
9
- validate_options!(options)
10
+ def initialize(output, options = {})
11
+ super
10
12
 
11
13
  PivotalTracker::Client.token = options["token"]
12
14
  begin
@@ -20,6 +22,7 @@ module AssistedWorkflow
20
22
 
21
23
  def find_story(story_id)
22
24
  if story_id.to_i > 0
25
+ log "loading story ##{story_id}"
23
26
  story = @project.stories.find(story_id)
24
27
  story.other_id = @username || @fullname
25
28
  story.other_id = story.other_id.to_s.downcase.split.join
@@ -28,16 +31,19 @@ module AssistedWorkflow
28
31
  end
29
32
 
30
33
  def start_story(story, options = {})
34
+ log "starting story ##{story.id}"
31
35
  update_story! story, options.merge(:current_state => "started")
32
36
  end
33
37
 
34
38
  def finish_story(story, options = {})
39
+ log "finishing story ##{story.id}"
35
40
  if update_story! story, :current_state => finished_state(story)
36
41
  story.notes.create(:text => options[:note]) if options[:note]
37
42
  end
38
43
  end
39
44
 
40
45
  def pending_stories(options = {})
46
+ log "loading pending stories"
41
47
  states = ["unstarted"]
42
48
  states << "started" if options[:include_started]
43
49
  @project.stories.all(:state => states, :owned_by => @fullname, :limit => 5)
@@ -49,17 +55,6 @@ module AssistedWorkflow
49
55
 
50
56
  private
51
57
 
52
- def validate_options!(options)
53
- if options.nil? || options.empty?
54
- raise AssistedWorkflow::Error, "pivotal missing configuration"
55
- end
56
- required_keys = %w(fullname token project_id)
57
- missing_keys = required_keys - options.keys
58
- if missing_keys.size > 0
59
- raise AssistedWorkflow::Error, "pivotal missing configuration: #{missing_keys.inspect}"
60
- end
61
- end
62
-
63
58
  def finished_state(story)
64
59
  if story.story_type == "chore"
65
60
  "accepted"
@@ -1,188 +1,158 @@
1
1
  require "assisted_workflow"
2
2
  require "thor"
3
3
 
4
- class AssistedWorkflow::CLI < Thor
5
- include Thor::Actions
6
- GLOBAL_CONFIG = File.expand_path(".awconfig", ENV["HOME"])
7
- LOCAL_CONFIG = ".awconfig"
8
- source_root(File.expand_path(File.join(__FILE__, "..", "templates")))
4
+ module AssistedWorkflow
5
+ class CLI < Thor
6
+ include Thor::Actions
7
+ GLOBAL_CONFIG = File.expand_path(".awconfig", ENV["HOME"])
8
+ LOCAL_CONFIG = ".awconfig"
9
+ source_root(File.expand_path(File.join(__FILE__, "..", "templates")))
9
10
 
10
- # tasks shortcuts
11
- map ["-v", "--version"] => :version
12
- map "s" => :start
13
- map "u" => :submit
14
- map "f" => :finish
11
+ # tasks shortcuts
12
+ map ["-v", "--version"] => :version
13
+ map "s" => :start
14
+ map "u" => :submit
15
+ map "f" => :finish
15
16
 
16
- desc "setup", "Setup initial configuration in current project directory"
17
- def setup
18
- copy_file "awconfig.global.tt", GLOBAL_CONFIG
19
- copy_file "awconfig.local.tt", LOCAL_CONFIG
20
- if File.exists?(".git")
21
- copy_file "commit-msg.tt", ".git/hooks/commit-msg"
22
- chmod ".git/hooks/commit-msg", "a+x"
23
- else
24
- raise AssistedWorkflow::Error, ".git folder not found"
17
+ desc "setup", "Setup initial configuration in current project directory"
18
+ def setup
19
+ copy_file "awconfig.global.tt", GLOBAL_CONFIG
20
+ copy_file "awconfig.local.tt", LOCAL_CONFIG
21
+ if File.exists?(".git")
22
+ copy_file "commit-msg.tt", ".git/hooks/commit-msg"
23
+ chmod ".git/hooks/commit-msg", "a+x"
24
+ else
25
+ raise AssistedWorkflow::Error, ".git folder not found"
26
+ end
27
+ out.next_command "set your own configuration running:", "" do |c|
28
+ c << "$ aw config pivotal.fullname='Your Pivotal User Name' --global"
29
+ c << "$ aw config pivotal.token=MYPIVOTALTOKEN --global"
30
+ c << "$ aw config github.token=MYGITHUBOAUTHTOKEN --global"
31
+ c << "$ aw config pivotal.project_id=00001"
32
+ end
25
33
  end
26
- say "set your own configuration editing the .awconfig files or running:", :green
27
- say_command "$ aw config pivotal.fullname='Flavio Granero' --global"
28
- say_command "$ aw config pivotal.token=MYPIVOTALTOKEN --global"
29
- say_command "$ aw config github.token=MYGITHUBOAUTHTOKEN --global"
30
- say_command "$ aw config pivotal.project_id=00001"
31
- end
32
34
 
33
- desc "start [STORY_ID]", "Start the pivotal story and create a new branch to receive the changes"
34
- method_option :all, :type => :boolean, :default => false, :aliases => "-a", :desc => "Show started and pending stories when no story_id is provided"
35
- method_option :estimate, :type => :numeric, :aliases => "-e", :desc => "Sets the story estimate when starting"
36
- def start(story_id=nil)
37
- check_awfile!
38
- story = pivotal.find_story(story_id)
39
- if story.nil?
40
- stories = pivotal.pending_stories(:include_started => options[:all])
41
- print_title "pending stories"
42
- print_stories(stories)
43
- say "start a story using:", :green
44
- say_command "$ aw start [STORY_ID]"
45
- else
46
- say_status "starting story", story.name
47
- pivotal.start_story(story, :estimate => options[:estimate])
48
- print_wrapped story.description, :indent => 2
49
- say "creating the feature branch"
50
- git.create_story_branch(story)
51
- say "after commiting your changes, submit a pull request using:", :green
52
- say_command "$ aw submit"
35
+ desc "start [STORY_ID]", "Start the pivotal story and create a new branch to receive the changes"
36
+ method_option :all, :type => :boolean, :default => false, :aliases => "-a", :desc => "Show started and pending stories when no story_id is provided"
37
+ method_option :estimate, :type => :numeric, :aliases => "-e", :desc => "Sets the story estimate when starting"
38
+ def start(story_id=nil)
39
+ check_awfile!
40
+ story = pivotal.find_story(story_id)
41
+ if story.nil?
42
+ stories = pivotal.pending_stories(:include_started => options[:all])
43
+ out.print_stories "pending stories", stories, options
44
+ out.next_command "start a story using:", "$ aw start [STORY_ID]"
45
+ else
46
+ pivotal.start_story(story, :estimate => options[:estimate])
47
+ out.print_story story
48
+ git.create_story_branch(story)
49
+ out.next_command "after commiting your changes, submit a pull request using:", "$ aw submit"
50
+ end
53
51
  end
54
- end
55
52
 
56
- desc "submit", "Submits the current story creating a new pull request"
57
- def submit
58
- check_awfile!
59
- story_id = git.current_story_id
60
- say "loading story info"
61
- story = pivotal.find_story(story_id)
62
- if story
63
- say "preparing local branch"
64
- git.rebase_and_push
65
- say "submiting the new pull request"
66
- pr = github.create_pull_request(git.repository, git.current_branch, story)
67
- say "finishing the story"
68
- pivotal.finish_story(story, :note => pr._links.html.href)
69
- say "new pull request: #{pr._links.html.href}", :yellow
70
- say "after pull request approval, remove the feature branch using:", :green
71
- say_command "$ aw finish"
72
- else
73
- raise AssistedWorkflow::Error, "story not found, make sure a feature branch in active"
53
+ desc "submit", "Submits the current story creating a new pull request"
54
+ def submit
55
+ check_awfile!
56
+ story_id = git.current_story_id
57
+ story = pivotal.find_story(story_id)
58
+ if story
59
+ git.rebase_and_push
60
+ pr_url = github.create_pull_request(
61
+ git.repository, git.current_branch, story
62
+ )
63
+ pivotal.finish_story(story, :note => pr_url)
64
+ out.next_command "after pull request approval, remove the feature branch using:", "$ aw finish"
65
+ else
66
+ raise AssistedWorkflow::Error, "story not found, make sure a feature branch in active"
67
+ end
74
68
  end
75
- end
76
69
 
77
- desc "finish", "Check if the changes are merged into master, removing the current feature branch"
78
- def finish
79
- check_awfile!
80
- story_id = git.current_story_id
81
- if story_id.to_i > 0
82
- if git.is_merged?
83
- say "removing local and remote feature branches"
70
+ desc "finish", "Check if the changes are merged into master, removing the current feature branch"
71
+ def finish
72
+ check_awfile!
73
+ story_id = git.current_story_id
74
+ if story_id.to_i > 0
75
+ git.check_merged!
84
76
  git.remove_branch
85
- say "well done! check your next stories using:", :green
86
- say_command "$ aw start"
77
+ out.next_command "well done! check your next stories using:", "$ aw start"
87
78
  else
88
- say "this branch is not merged into master yet", :yellow
79
+ raise AssistedWorkflow::Error, "story not found, make sure a feature branch in active"
89
80
  end
90
- else
91
- raise AssistedWorkflow::Error, "story not found, make sure a feature branch in active"
92
81
  end
93
- end
94
82
 
95
- desc "version", "Display assisted_workflow gem version"
96
- def version
97
- say AssistedWorkflow::VERSION
98
- end
83
+ desc "version", "Display assisted_workflow gem version"
84
+ def version
85
+ say AssistedWorkflow::VERSION
86
+ end
99
87
 
100
- desc "config group.key=value", "Set configuration keys in local config file"
101
- method_option :global, :type => :boolean, :aliases => "-g", :desc => "Set configuration key in global configuration file (for all projects)"
102
- def config(*args)
103
- if args.empty?
104
- print_table configuration.to_hash
105
- else
106
- config_file.parse(args).save!
88
+ desc "config group.key=value", "Set configuration keys in local config file"
89
+ method_option :global, :type => :boolean, :aliases => "-g", :desc => "Set configuration key in global configuration file (for all projects)"
90
+ def config(*args)
91
+ if args.empty?
92
+ print_table configuration.to_hash
93
+ else
94
+ config_file.parse(args).save!
95
+ end
107
96
  end
108
- end
109
97
 
110
- desc "thanks", "Aw, Thanks!", :hide => true
111
- def thanks
112
- say "you're welcome!", :on_magenta
113
- end
98
+ desc "thanks", "Aw, Thanks!", :hide => true
99
+ def thanks
100
+ out.say "you're welcome!", :on_magenta
101
+ end
114
102
 
115
103
 
116
- no_tasks do
117
- def pivotal
118
- @pivotal ||= AssistedWorkflow::Pivotal.new(configuration[:pivotal])
119
- end
104
+ no_tasks do
105
+ def out
106
+ @out ||= Output.new(self.shell)
107
+ end
108
+
109
+ def pivotal
110
+ @pivotal ||= Addons::Pivotal.new(out, configuration[:pivotal])
111
+ end
120
112
 
121
- def git
122
- @git ||= AssistedWorkflow::Git.new
123
- end
113
+ def git
114
+ @git ||= Addons::Git.new(out)
115
+ end
124
116
 
125
- def github
126
- @github ||= AssistedWorkflow::Github.new(configuration[:github])
127
- end
117
+ def github
118
+ @github ||= Addons::Github.new(out, configuration[:github])
119
+ end
128
120
 
129
- def config_file
130
- @config_file ||= AssistedWorkflow::ConfigFile.new(awfile)
131
- end
121
+ def config_file
122
+ @config_file ||= ConfigFile.new(awfile)
123
+ end
132
124
 
133
- # loads all configuration, merging global and local values
134
- def configuration
135
- @configuration ||= begin
136
- AssistedWorkflow::ConfigFile.new(GLOBAL_CONFIG).merge_file(LOCAL_CONFIG)
137
- rescue TypeError
138
- raise AssistedWorkflow::Error, "Error on loading .awconfig files. Please check the content format."
125
+ # loads all configuration, merging global and local values
126
+ def configuration
127
+ @configuration ||= begin
128
+ ConfigFile.new(GLOBAL_CONFIG).merge_file(LOCAL_CONFIG)
129
+ rescue TypeError
130
+ raise AssistedWorkflow::Error, "Error on loading .awconfig files. Please check the content format."
131
+ end
139
132
  end
140
133
  end
141
- end
142
134
 
143
- class << self
144
- def start(given_args=ARGV, config={})
145
- super
146
- rescue AssistedWorkflow::Error => e
147
- config[:shell].say e.message, :red
148
- exit(1)
135
+ class << self
136
+ def start(given_args=ARGV, config={})
137
+ super
138
+ rescue AssistedWorkflow::Error => e
139
+ config[:shell].say e.message, :red
140
+ exit(1)
141
+ end
149
142
  end
150
- end
151
143
 
152
- private ######################################################################
144
+ private ##################################################################
153
145
 
154
- def print_title(title)
155
- say "-" * title.length, :green
156
- say title.upcase, :green
157
- say "-" * title.length, :green
158
- end
159
-
160
- def print_stories(stories)
161
- rows = stories.map do |story|
162
- if options[:all]
163
- [story.id, story.current_state, story.name]
164
- else
165
- [story.id, story.estimate, story.name]
166
- end
146
+ def check_awfile!
147
+ raise AssistedWorkflow::Error, "#{awfile} does not exist.\nmake sure you run `$ aw setup` in your project folder." unless File.exist?(awfile)
167
148
  end
168
- print_table(rows)
169
- end
170
-
171
- def say_command(command)
172
- with_padding do
173
- say command
174
- end
175
- end
176
-
177
- def check_awfile!
178
- raise AssistedWorkflow::Error, "#{awfile} does not exist.\nmake sure you run `$ aw setup` in your project folder." unless File.exist?(awfile)
179
- end
180
149
 
181
- def awfile
182
- case
183
- when options[:awfile] then options[:awfile]
184
- when options[:global] then GLOBAL_CONFIG
185
- else LOCAL_CONFIG
150
+ def awfile
151
+ case
152
+ when options[:awfile] then options[:awfile]
153
+ when options[:global] then GLOBAL_CONFIG
154
+ else LOCAL_CONFIG
155
+ end
186
156
  end
187
- end
157
+ end
188
158
  end
@@ -8,7 +8,8 @@ module AssistedWorkflow
8
8
 
9
9
  DESCRIPTION_LIMIT = 30
10
10
 
11
- def initialize(options = {})
11
+ def initialize(output, options = {})
12
+ super
12
13
  @command_options = {:raise_error => true}.merge(options)
13
14
  end
14
15
 
@@ -16,6 +17,7 @@ module AssistedWorkflow
16
17
  # the branch name format is:
17
18
  # => story_onwer_username.story_id.story_name
18
19
  def create_story_branch(story)
20
+ log "creating the new branch"
19
21
  branch = branch_name(story)
20
22
  git "checkout -b #{branch}"
21
23
  # git "push --set-upstream origin #{branch}"
@@ -23,6 +25,7 @@ module AssistedWorkflow
23
25
 
24
26
  # run all the git steps required for a clean pull request
25
27
  def rebase_and_push
28
+ log "preparing local branch"
26
29
  check_everything_commited!
27
30
  branch = current_branch
28
31
  git "checkout master"
@@ -50,18 +53,21 @@ module AssistedWorkflow
50
53
  end
51
54
 
52
55
  # check if current branch is merged into master
53
- def is_merged?
56
+ def check_merged!
54
57
  check_everything_commited!
55
58
  branch = current_branch
56
59
  git "checkout master"
57
60
  git "pull --rebase"
58
61
  merged = git("branch --merged").include?(branch)
59
62
  git "checkout #{branch}"
60
- merged
63
+ unless merged
64
+ raise AssistedWorkflow::Error, "this branch is not merged into master"
65
+ end
61
66
  end
62
67
 
63
68
  # removes current branch and its remote version
64
69
  def remove_branch
70
+ log "removing local and remote feature branches"
65
71
  branch = current_branch
66
72
  git "push origin :#{branch}", :raise_error => false
67
73
  git "checkout master"
@@ -72,7 +78,7 @@ module AssistedWorkflow
72
78
 
73
79
  def git(command, options = {})
74
80
  options = @command_options.merge(options)
75
- puts "git #{command}" unless options[:silent] == true
81
+ # log("git #{command}", :step => true) unless options[:silent] == true
76
82
  result = system("git #{command}")
77
83
  if system_error? && options[:raise_error]
78
84
  msg = ["git command error", options[:error]].compact.join(": ")
@@ -0,0 +1,54 @@
1
+ module AssistedWorkflow
2
+
3
+ # a helper class to provide custom shell print methods
4
+ class Output < SimpleDelegator
5
+ def initialize(shell)
6
+ super
7
+ @shell = shell
8
+ end
9
+
10
+ # prints a wrapped gray line, showing as comments between log lines
11
+ def say_comment(comment)
12
+ @shell.padding = 4
13
+ say comment, [:black, :bold]
14
+ @shell.padding = 0
15
+ end
16
+
17
+ # prints a highlighted title section
18
+ def print_title(title)
19
+ say "-" * title.length, :green
20
+ say title.upcase, :green
21
+ say "-" * title.length, :green
22
+ end
23
+
24
+ # prints as table with stories data
25
+ def print_stories(title, stories, options = {})
26
+ print_title title
27
+ rows = stories.map do |story|
28
+ if options[:all]
29
+ [story.id, story.current_state, story.name]
30
+ else
31
+ [story.id, story.estimate, story.name]
32
+ end
33
+ end
34
+ print_table(rows)
35
+ end
36
+
37
+ def print_story(story)
38
+ say "-" * 40
39
+ print_wrapped story.name, :indent => 2
40
+ print_wrapped story.description, :indent => 2
41
+ say "-" * 40
42
+ end
43
+
44
+ def next_command(title, commands, &block)
45
+ say title, :green
46
+ _commands = Array(commands)
47
+ yield(_commands) if block_given?
48
+ _commands.each do |command|
49
+ print_wrapped command, :indent => 2
50
+ end
51
+ end
52
+
53
+ end
54
+ end
@@ -1,3 +1,3 @@
1
1
  module AssistedWorkflow
2
- VERSION = "0.1.4"
2
+ VERSION = "0.2.0"
3
3
  end
@@ -1,9 +1,9 @@
1
1
  require 'spec_helper'
2
- require 'assisted_workflow/git'
2
+ require 'assisted_workflow/addons/git'
3
3
 
4
- describe AssistedWorkflow::Git do
4
+ describe AssistedWorkflow::Addons::Git do
5
5
  before do
6
- @git = AssistedWorkflow::Git.new(:silent => true)
6
+ @git = AssistedWorkflow::Addons::Git.new(nil, :silent => true)
7
7
  stub(@git).system_error?{ false }
8
8
  stub(@git).system("git rev-parse --abbrev-ref HEAD"){ "flavio.00001.new_feature"}
9
9
  end
@@ -16,7 +16,7 @@ describe AssistedWorkflow::Git do
16
16
  it "raises a git error when git command does not exit with success" do
17
17
  mock(@git).system_error?{ true }
18
18
  mock(@git).system("git checkout -b flavio.00001.new_feature")
19
- proc { @git.create_story_branch(story) }.must_raise AssistedWorkflow::GitError, "git command error"
19
+ proc { @git.create_story_branch(story) }.must_raise AssistedWorkflow::Addons::GitError, "git command error"
20
20
  end
21
21
 
22
22
 
@@ -1,7 +1,7 @@
1
1
  require 'spec_helper'
2
- require 'assisted_workflow/github'
2
+ require 'assisted_workflow/addons/github'
3
3
 
4
- describe AssistedWorkflow::Github do
4
+ describe AssistedWorkflow::Addons::Github do
5
5
  before do
6
6
  @configuration = {
7
7
  "token" => "mygithubtoken",
@@ -11,7 +11,7 @@ describe AssistedWorkflow::Github do
11
11
  stub(@client).user_authenticated?{ true }
12
12
  stub(Octokit::Client).new{ @client }
13
13
 
14
- @github = AssistedWorkflow::Github.new(@configuration)
14
+ @github = AssistedWorkflow::Addons::Github.new(nil, @configuration)
15
15
  end
16
16
 
17
17
  it "initializes a valid github wrapper" do
@@ -20,15 +20,15 @@ describe AssistedWorkflow::Github do
20
20
 
21
21
  it "requires token" do
22
22
  proc {
23
- AssistedWorkflow::Github.new({})
23
+ AssistedWorkflow::Addons::Github.new(nil, {})
24
24
  }.must_raise AssistedWorkflow::Error, "github missing configuration:[token]"
25
25
  end
26
26
 
27
27
  it "creates a new valid pull request" do
28
- mock(@client).create_pull_request("flaviogranero/assisted_workflow", "master", "flavio.00001.new_feature", "[#00001] New Feature", "Feature description"){ true }
28
+ mock(@client).create_pull_request("flaviogranero/assisted_workflow", "master", "flavio.00001.new_feature", "[#00001] New Feature", "Feature description"){ pull_request }
29
29
  @github.create_pull_request(
30
30
  "flaviogranero/assisted_workflow", "flavio.00001.new_feature", story
31
- )
31
+ ).must_match /flaviogranero\/assisted_workflow\/pull\/1/
32
32
  end
33
33
 
34
34
  it "raises on creating an invalid pull request" do
@@ -45,4 +45,10 @@ describe AssistedWorkflow::Github do
45
45
  def story
46
46
  @story ||= PivotalTracker::Story.new(:id => "00001", :name => "New Feature", :description => "Feature description")
47
47
  end
48
+
49
+ def pull_request
50
+ agent = Sawyer::Agent.new("", {:links_parser => Sawyer::LinkParsers::Simple.new})
51
+ data = {_links: {html: {href: "https://github.com/flaviogranero/assisted_workflow/pull/1"}}}
52
+ Sawyer::Resource.new(agent, data)
53
+ end
48
54
  end
@@ -1,7 +1,7 @@
1
1
  require 'spec_helper'
2
- require 'assisted_workflow/pivotal'
2
+ require 'assisted_workflow/addons/pivotal'
3
3
 
4
- describe AssistedWorkflow::Pivotal do
4
+ describe AssistedWorkflow::Addons::Pivotal do
5
5
 
6
6
  before do
7
7
  @configuration = {
@@ -14,7 +14,7 @@ describe AssistedWorkflow::Pivotal do
14
14
  @project = PivotalTracker::Project.new(:id => "1")
15
15
  stub(PivotalTracker::Project).find(@configuration["project_id"]){ @project }
16
16
 
17
- @pivotal = AssistedWorkflow::Pivotal.new(@configuration)
17
+ @pivotal = AssistedWorkflow::Addons::Pivotal.new(nil, @configuration)
18
18
  end
19
19
 
20
20
  it "initializes a valid pivotal wrapper" do
@@ -23,7 +23,8 @@ describe AssistedWorkflow::Pivotal do
23
23
 
24
24
  it "requires fullname" do
25
25
  proc {
26
- AssistedWorkflow::Pivotal.new(
26
+ AssistedWorkflow::Addons::Pivotal.new(
27
+ nil,
27
28
  @configuration.reject{|k,v| k == "fullname"}
28
29
  )
29
30
  }.must_raise AssistedWorkflow::Error, "pivotal missing configuration:[fullname]"
@@ -31,7 +32,8 @@ describe AssistedWorkflow::Pivotal do
31
32
 
32
33
  it "requires token" do
33
34
  proc {
34
- AssistedWorkflow::Pivotal.new(
35
+ AssistedWorkflow::Addons::Pivotal.new(
36
+ nil,
35
37
  @configuration.reject{|k,v| k == "token"}
36
38
  )
37
39
  }.must_raise AssistedWorkflow::Error, "pivotal missing configuration:[token]"
@@ -39,7 +41,8 @@ describe AssistedWorkflow::Pivotal do
39
41
 
40
42
  it "requires project_id" do
41
43
  proc {
42
- AssistedWorkflow::Pivotal.new(
44
+ AssistedWorkflow::Addons::Pivotal.new(
45
+ nil,
43
46
  @configuration.reject{|k,v| k == "project_id"}
44
47
  )
45
48
  }.must_raise AssistedWorkflow::Error, "pivotal missing configuration:[project_id]"
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: assisted_workflow
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.4
4
+ version: 0.2.0
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2014-02-07 00:00:00.000000000 Z
12
+ date: 2014-02-14 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: rake
@@ -144,20 +144,23 @@ files:
144
144
  - assisted_workflow.gemspec
145
145
  - bin/aw
146
146
  - lib/assisted_workflow.rb
147
+ - lib/assisted_workflow/addons/base.rb
148
+ - lib/assisted_workflow/addons/git.rb
149
+ - lib/assisted_workflow/addons/github.rb
150
+ - lib/assisted_workflow/addons/pivotal.rb
147
151
  - lib/assisted_workflow/cli.rb
148
152
  - lib/assisted_workflow/config_file.rb
149
153
  - lib/assisted_workflow/exceptions.rb
150
154
  - lib/assisted_workflow/git.rb
151
- - lib/assisted_workflow/github.rb
152
- - lib/assisted_workflow/pivotal.rb
155
+ - lib/assisted_workflow/output.rb
153
156
  - lib/assisted_workflow/templates/awconfig.global.tt
154
157
  - lib/assisted_workflow/templates/awconfig.local.tt
155
158
  - lib/assisted_workflow/templates/commit-msg.tt
156
159
  - lib/assisted_workflow/version.rb
160
+ - spec/assisted_workflow/addons/git_spec.rb
161
+ - spec/assisted_workflow/addons/github_spec.rb
162
+ - spec/assisted_workflow/addons/pivotal_spec.rb
157
163
  - spec/assisted_workflow/config_file_spec.rb
158
- - spec/assisted_workflow/git_spec.rb
159
- - spec/assisted_workflow/github_spec.rb
160
- - spec/assisted_workflow/pivotal_spec.rb
161
164
  - spec/spec_helper.rb
162
165
  homepage: https://github.com/flaviogranero/assisted_workflow
163
166
  licenses:
@@ -216,7 +219,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
216
219
  version: '0'
217
220
  segments:
218
221
  - 0
219
- hash: 2646088369177769038
222
+ hash: -50568132931744746
220
223
  required_rubygems_version: !ruby/object:Gem::Requirement
221
224
  none: false
222
225
  requirements:
@@ -225,7 +228,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
225
228
  version: '0'
226
229
  segments:
227
230
  - 0
228
- hash: 2646088369177769038
231
+ hash: -50568132931744746
229
232
  requirements: []
230
233
  rubyforge_project:
231
234
  rubygems_version: 1.8.24
@@ -234,8 +237,8 @@ specification_version: 3
234
237
  summary: AW is a CLI tool to automate software development workflows based on github
235
238
  pull requests
236
239
  test_files:
240
+ - spec/assisted_workflow/addons/git_spec.rb
241
+ - spec/assisted_workflow/addons/github_spec.rb
242
+ - spec/assisted_workflow/addons/pivotal_spec.rb
237
243
  - spec/assisted_workflow/config_file_spec.rb
238
- - spec/assisted_workflow/git_spec.rb
239
- - spec/assisted_workflow/github_spec.rb
240
- - spec/assisted_workflow/pivotal_spec.rb
241
244
  - spec/spec_helper.rb