git_workflow 0.0.5
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/README.markdown +77 -0
- data/Rakefile +33 -0
- data/bin/git-finish +4 -0
- data/bin/git-start +4 -0
- data/bin/git-workflow-setup +4 -0
- data/features/core_functionality/4049578_need_the_ability_to_start_a_new_branch.feature +15 -0
- data/features/core_functionality/4049611_need_the_ability_to_finish_a_specified_branch.feature +17 -0
- data/features/core_functionality/4056359_start_with_local_branch_already_present.feature +16 -0
- data/features/core_functionality/4056363_finish_the_current_branch.feature +17 -0
- data/features/core_functionality/4056389_changes_to_pt_story_name_cause_branch_issues.feature +25 -0
- data/features/core_functionality/4135658_control_output_verbosity_using_v_switch.feature +32 -0
- data/features/core_functionality/4468313_get_config_value_for_is_producing_an_error_log.feature +43 -0
- data/features/extensions/4058326_display_story_description_on_start.feature +14 -0
- data/features/git_branching/4135501_allow_branch_start_point_to_be_specified_from_command_line.feature +27 -0
- data/features/hooks/4069174_investigate_the_effort_required_to_add_pre_amp_post_hooks.feature +24 -0
- data/features/hooks/4199841_need_hooks_for_my_workflow.feature +51 -0
- data/features/hooks/4199845_need_hooks_for_sanger_workflow.feature +66 -0
- data/features/hooks/4205913_output_from_rake_tests_should_be_seen.feature +19 -0
- data/features/hooks/4424828_git_start_is_missing_pt_integration_for_my_hooks.feature +15 -0
- data/features/pivotal_tracker_api/4133291_chores_go_straight_to_accepted_not_to_finished.feature +15 -0
- data/features/release/4132264_fix_the_libxml_warnings_from_nokogiri.feature +20 -0
- data/features/step_definitions/aruba_extensions.rb +4 -0
- data/features/step_definitions/configuration_steps.rb +38 -0
- data/features/step_definitions/git_steps.rb +102 -0
- data/features/step_definitions/misc_steps.rb +3 -0
- data/features/step_definitions/pivotal_tracker_steps.rb +43 -0
- data/features/step_definitions/project_code_steps.rb +35 -0
- data/features/support/aruba.rb +1 -0
- data/features/support/hooks/configuration.rb +4 -0
- data/features/support/hooks/environment.rb +49 -0
- data/features/support/hooks/pivotal_tracker.rb +170 -0
- data/lib/git_workflow.rb +5 -0
- data/lib/git_workflow/callbacks.rb +16 -0
- data/lib/git_workflow/callbacks/pivotal_tracker_support.rb +64 -0
- data/lib/git_workflow/callbacks/remote_git_branch_support.rb +9 -0
- data/lib/git_workflow/callbacks/styles/debug.rb +58 -0
- data/lib/git_workflow/callbacks/styles/default.rb +43 -0
- data/lib/git_workflow/callbacks/styles/mine.rb +52 -0
- data/lib/git_workflow/callbacks/styles/sanger.rb +48 -0
- data/lib/git_workflow/callbacks/test_code_support.rb +29 -0
- data/lib/git_workflow/command_line.rb +46 -0
- data/lib/git_workflow/commands.rb +4 -0
- data/lib/git_workflow/commands/base.rb +31 -0
- data/lib/git_workflow/commands/finish.rb +36 -0
- data/lib/git_workflow/commands/setup.rb +157 -0
- data/lib/git_workflow/commands/start.rb +30 -0
- data/lib/git_workflow/configuration.rb +93 -0
- data/lib/git_workflow/core_ext.rb +106 -0
- data/lib/git_workflow/git.rb +143 -0
- data/lib/git_workflow/logger.yaml +27 -0
- data/lib/git_workflow/logging.rb +77 -0
- data/lib/git_workflow/story.rb +96 -0
- data/spec/core_functionality/4056539_support_http_proxy_spec.rb +68 -0
- data/spec/core_functionality/4058365_bad_request_on_story_update_spec.rb +13 -0
- data/spec/core_functionality/4058394_make_commands_more_verbose_spec.rb +41 -0
- data/spec/core_functionality/4058719_error_if_none_of_the_required_configuration_values_are_set_spec.rb +21 -0
- data/spec/core_functionality/4058861_git_config_returns_empty_strings_which_should_be_nil_spec.rb +59 -0
- data/spec/core_functionality/4172431_add_git_workflow_setup_command_to_make_setup_easier_spec.rb +148 -0
- data/spec/core_functionality/4199841_need_callbacks_for_my_workflow_spec.rb +97 -0
- data/spec/extensions/4199841_need_callbacks_for_my_workflow_spec.rb +167 -0
- data/spec/extensions/4205913_output_from_rake_tests_should_be_seen_spec.rb +34 -0
- data/spec/git_branching/4058723_branches_end_in_if_the_last_character_is_invalid_spec.rb +40 -0
- data/spec/git_branching/4059824_code_is_not_using_workflow_localbranchconvention_to_decode_branch_names_on_finish_spec.rb +115 -0
- data/spec/git_branching/4216087_support_pushing_branches_spec.rb +44 -0
- data/spec/hooks/4199845_need_hooks_for_sanger_workflow_spec.rb +27 -0
- data/spec/pivotal_tracker_api/4056381_pt_api_token_not_being_passed_in_headers_spec.rb +40 -0
- data/spec/pivotal_tracker_api/4056638_library_code_using_localhost_spec.rb +16 -0
- data/spec/pivotal_tracker_api/4056661_content_type_header_should_be_text_xml_on_updates_spec.rb +16 -0
- data/spec/pivotal_tracker_api/4058718_if_pt_username_is_not_set_use_user_name_spec.rb +26 -0
- data/spec/pivotal_tracker_api/4146016_decode_the_xml_encoded_text_of_description_and_name_spec.rb +63 -0
- data/spec/shared_examples/configuration.rb +10 -0
- data/spec/shared_examples/story.rb +17 -0
- data/spec/spec_helper.rb +18 -0
- metadata +220 -0
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
log4r_config:
|
|
2
|
+
# Here we define all of the loggers that are going to be used across all of the
|
|
3
|
+
# possible configurations.
|
|
4
|
+
loggers:
|
|
5
|
+
- name: Console
|
|
6
|
+
level: DEBUG
|
|
7
|
+
outputters:
|
|
8
|
+
- normal_information
|
|
9
|
+
- verbose_information
|
|
10
|
+
|
|
11
|
+
# And here are the outputters and with their associated formatters.
|
|
12
|
+
outputters:
|
|
13
|
+
- name: normal_information
|
|
14
|
+
type: StdoutOutputter
|
|
15
|
+
only_at:
|
|
16
|
+
- INFO
|
|
17
|
+
- FATAL
|
|
18
|
+
formatter:
|
|
19
|
+
type: PatternFormatter
|
|
20
|
+
pattern: '%l: %m'
|
|
21
|
+
|
|
22
|
+
- name: verbose_information
|
|
23
|
+
type: StderrOutputter
|
|
24
|
+
level: FATAL
|
|
25
|
+
formatter:
|
|
26
|
+
type: PatternFormatter
|
|
27
|
+
pattern: '%l: %m'
|
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
require 'log4r'
|
|
2
|
+
require 'log4r/yamlconfigurator'
|
|
3
|
+
|
|
4
|
+
module Log4r
|
|
5
|
+
class Outputter
|
|
6
|
+
def initialize_with_multiple_levels(name, hash = {})
|
|
7
|
+
initialize_without_multiple_levels(name, hash)
|
|
8
|
+
self.only_at(*hash[ :only_at ]) if hash.key?(:only_at)
|
|
9
|
+
end
|
|
10
|
+
alias_method_chain(:initialize, :multiple_levels)
|
|
11
|
+
end
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
module GitWorkflow
|
|
15
|
+
module Logging
|
|
16
|
+
# Causes the loading of the logging information before anything else is done.
|
|
17
|
+
Log4r::YamlConfigurator.load_yaml_file(File.expand_path(File.join(File.dirname(__FILE__), 'logger.yaml')))
|
|
18
|
+
|
|
19
|
+
def self.included(base)
|
|
20
|
+
base.instance_eval do
|
|
21
|
+
extend ClassMethods
|
|
22
|
+
|
|
23
|
+
[ :debug, :info, :error ].each do |level|
|
|
24
|
+
class_eval <<-END_OF_LOGGING_METHOD
|
|
25
|
+
def #{ level }(message, &block)
|
|
26
|
+
self.class.#{ level }(message, &block)
|
|
27
|
+
end
|
|
28
|
+
|
|
29
|
+
def self.#{ level }(message, &block)
|
|
30
|
+
self.log(#{ level.inspect }, message, &block)
|
|
31
|
+
end
|
|
32
|
+
END_OF_LOGGING_METHOD
|
|
33
|
+
end
|
|
34
|
+
end
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
class << self
|
|
38
|
+
def logger=(logger)
|
|
39
|
+
@logger = logger
|
|
40
|
+
end
|
|
41
|
+
|
|
42
|
+
def logger
|
|
43
|
+
@logger ||= default_logger
|
|
44
|
+
end
|
|
45
|
+
|
|
46
|
+
def default_logger
|
|
47
|
+
Log4r::Logger['Console']
|
|
48
|
+
end
|
|
49
|
+
end
|
|
50
|
+
|
|
51
|
+
module ClassMethods
|
|
52
|
+
def logger=(logger)
|
|
53
|
+
@logger = logger
|
|
54
|
+
end
|
|
55
|
+
|
|
56
|
+
def logger
|
|
57
|
+
@logger || GitWorkflow::Logging.logger
|
|
58
|
+
end
|
|
59
|
+
|
|
60
|
+
def log(level, message, &block)
|
|
61
|
+
if block_given?
|
|
62
|
+
begin
|
|
63
|
+
logger.send(level, "(start): #{ message }")
|
|
64
|
+
rc = yield
|
|
65
|
+
logger.send(level, "(finish): #{ message }")
|
|
66
|
+
rc
|
|
67
|
+
rescue => exception
|
|
68
|
+
logger.error("#{ message } (#{ exception.message })")
|
|
69
|
+
raise
|
|
70
|
+
end
|
|
71
|
+
else
|
|
72
|
+
logger.send(level, message)
|
|
73
|
+
end
|
|
74
|
+
end
|
|
75
|
+
end
|
|
76
|
+
end
|
|
77
|
+
end
|
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
require 'rest_client'
|
|
2
|
+
require 'builder'
|
|
3
|
+
|
|
4
|
+
# On MacOSX systems you can have a dodgy LibXML2 which Nokogiri warns about. Hide this warning
|
|
5
|
+
# by setting the following constant:
|
|
6
|
+
I_KNOW_I_AM_USING_AN_OLD_AND_BUGGY_VERSION_OF_LIBXML2 = true
|
|
7
|
+
require 'nokogiri'
|
|
8
|
+
|
|
9
|
+
module GitWorkflow
|
|
10
|
+
class Story
|
|
11
|
+
include Logging
|
|
12
|
+
|
|
13
|
+
attr_reader :story_id
|
|
14
|
+
attr_reader :name
|
|
15
|
+
attr_reader :description
|
|
16
|
+
|
|
17
|
+
def initialize(service)
|
|
18
|
+
@service = service
|
|
19
|
+
load_story!
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
def branch_name
|
|
23
|
+
@local_branch_name ||= GitWorkflow::Configuration.instance.local_branch_convention.to(self)
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
def remote_branch_name
|
|
27
|
+
@remote_branch_name ||= GitWorkflow::Configuration.instance.remote_branch_convention.to(self)
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
def start_state
|
|
31
|
+
'started'
|
|
32
|
+
end
|
|
33
|
+
|
|
34
|
+
def finish_state
|
|
35
|
+
@story_type == 'chore' ? 'accepted' : 'finished'
|
|
36
|
+
end
|
|
37
|
+
|
|
38
|
+
def comment(message)
|
|
39
|
+
_service!(:post, 'notes') do |xml|
|
|
40
|
+
xml.note {
|
|
41
|
+
xml.text(message)
|
|
42
|
+
}
|
|
43
|
+
end
|
|
44
|
+
end
|
|
45
|
+
|
|
46
|
+
def service!(&block)
|
|
47
|
+
_service!(:put) do |xml|
|
|
48
|
+
xml.story {
|
|
49
|
+
xml.owned_by(GitWorkflow::Configuration.instance.username)
|
|
50
|
+
yield(xml) if block_given?
|
|
51
|
+
}
|
|
52
|
+
end
|
|
53
|
+
end
|
|
54
|
+
|
|
55
|
+
private
|
|
56
|
+
|
|
57
|
+
def _service!(action, subresource = nil, &block)
|
|
58
|
+
xml = Builder::XmlMarkup.new
|
|
59
|
+
yield(xml)
|
|
60
|
+
service = @service
|
|
61
|
+
service = service[subresource] unless subresource.nil?
|
|
62
|
+
service.send(action, xml.target!, :content_type => 'application/xml')
|
|
63
|
+
rescue RestClient::ExceptionWithResponse => exception
|
|
64
|
+
error('Cannot seem to perform operation with PT:')
|
|
65
|
+
error(exception.response)
|
|
66
|
+
raise
|
|
67
|
+
end
|
|
68
|
+
|
|
69
|
+
class XmlWrapper
|
|
70
|
+
def initialize(xml)
|
|
71
|
+
@xml = Nokogiri::XML(xml)
|
|
72
|
+
end
|
|
73
|
+
|
|
74
|
+
def required!(element)
|
|
75
|
+
value = optional(element)
|
|
76
|
+
raise MissingElement, "Missing '#{ element }' in the PT XML" if value.blank?
|
|
77
|
+
value
|
|
78
|
+
end
|
|
79
|
+
|
|
80
|
+
def optional(element)
|
|
81
|
+
values = @xml.xpath("/story/#{ element }/text()")
|
|
82
|
+
values.empty? ? nil : values.first.content
|
|
83
|
+
end
|
|
84
|
+
end
|
|
85
|
+
|
|
86
|
+
def load_story!
|
|
87
|
+
info("Retrieving story information") do
|
|
88
|
+
xml = XmlWrapper.new(@service.get)
|
|
89
|
+
@story_id = xml.required!(:id).to_i
|
|
90
|
+
@story_type = xml.required!(:story_type)
|
|
91
|
+
@name = xml.required!(:name)
|
|
92
|
+
@description = xml.optional(:description)
|
|
93
|
+
end
|
|
94
|
+
end
|
|
95
|
+
end
|
|
96
|
+
end
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
require 'spec_helper'
|
|
2
|
+
require 'git_workflow/callbacks/pivotal_tracker_support'
|
|
3
|
+
|
|
4
|
+
describe GitWorkflow::Callbacks::PivotalTrackerSupport::ClassMethods do
|
|
5
|
+
before(:each) do
|
|
6
|
+
@command = Object.new
|
|
7
|
+
@command.stub!(:debug).with(any_args)
|
|
8
|
+
@command.extend(GitWorkflow::Callbacks::PivotalTrackerSupport::ClassMethods)
|
|
9
|
+
end
|
|
10
|
+
|
|
11
|
+
describe '.value_of_environment_variable' do
|
|
12
|
+
before(:each) do
|
|
13
|
+
ENV['somevariable'] = 'this is the value'
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
after(:each) do
|
|
17
|
+
ENV['somevariable'] = nil
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
it 'returns the value of the environment variable' do
|
|
21
|
+
@command.value_of_environment_variable('somevariable').should == 'this is the value'
|
|
22
|
+
end
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
describe '.enable_http_proxy_if_present' do
|
|
26
|
+
after(:each) do
|
|
27
|
+
@command.enable_http_proxy_if_present
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
it 'uses the $http_proxy environment variable first' do
|
|
31
|
+
@command.stub!(:value_of_environment_variable).with('http_proxy').and_return('http_proxy value')
|
|
32
|
+
RestClient.should_receive(:proxy=).with('http_proxy value')
|
|
33
|
+
end
|
|
34
|
+
|
|
35
|
+
it 'falls back to $HTTP_PROXY' do
|
|
36
|
+
@command.stub!(:value_of_environment_variable).with('http_proxy').and_return(nil)
|
|
37
|
+
@command.stub!(:value_of_environment_variable).with('HTTP_PROXY').and_return('HTTP_PROXY value')
|
|
38
|
+
RestClient.should_receive(:proxy=).with('HTTP_PROXY value')
|
|
39
|
+
end
|
|
40
|
+
|
|
41
|
+
it 'does not set the HTTP proxy if neither is set' do
|
|
42
|
+
@command.stub!(:value_of_environment_variable).with('http_proxy').and_return(nil)
|
|
43
|
+
@command.stub!(:value_of_environment_variable).with('HTTP_PROXY').and_return(nil)
|
|
44
|
+
RestClient.should_receive(:proxy=).with(anything).never
|
|
45
|
+
end
|
|
46
|
+
end
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
describe GitWorkflow::Callbacks::PivotalTrackerSupport do
|
|
50
|
+
before(:each) do
|
|
51
|
+
@command = Class.new.new
|
|
52
|
+
@command.stub!(:debug).with(any_args)
|
|
53
|
+
@command.extend(GitWorkflow::Callbacks::PivotalTrackerSupport)
|
|
54
|
+
end
|
|
55
|
+
|
|
56
|
+
describe '#pivotal_tracker_service' do
|
|
57
|
+
it_should_behave_like 'it needs configuration'
|
|
58
|
+
|
|
59
|
+
it 'enables the HTTP proxy' do
|
|
60
|
+
@command.class.instance_eval do
|
|
61
|
+
should_receive(:enable_http_proxy_if_present).once
|
|
62
|
+
should_receive(:pivotal_tracker_url_for).with('project_id', 'story_id').and_return('url')
|
|
63
|
+
end
|
|
64
|
+
RestClient::Resource.stub!(:new).with(any_args).and_return(:ok)
|
|
65
|
+
@command.pivotal_tracker_service_for('story_id')
|
|
66
|
+
end
|
|
67
|
+
end
|
|
68
|
+
end
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
require 'spec_helper'
|
|
2
|
+
|
|
3
|
+
describe GitWorkflow do
|
|
4
|
+
it_should_behave_like 'it needs configuration'
|
|
5
|
+
it_should_behave_like 'it needs a working Story'
|
|
6
|
+
|
|
7
|
+
describe '#service!' do
|
|
8
|
+
it 'generates valid XML' do
|
|
9
|
+
@service.should_receive(:put).with('<story><owned_by>username</owned_by></story>', anything)
|
|
10
|
+
@story.service!
|
|
11
|
+
end
|
|
12
|
+
end
|
|
13
|
+
end
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
require 'spec_helper'
|
|
2
|
+
|
|
3
|
+
describe GitWorkflow::Logging::ClassMethods do
|
|
4
|
+
before(:each) do
|
|
5
|
+
@object = Class.new(Object).new
|
|
6
|
+
@object.class.send(:include, GitWorkflow::Logging::ClassMethods)
|
|
7
|
+
|
|
8
|
+
@logger = mock('Logger')
|
|
9
|
+
@object.logger = @logger
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
describe '#log' do
|
|
13
|
+
it 'displays just the message and the level if no block given' do
|
|
14
|
+
@logger.should_receive(:debug).with('my message')
|
|
15
|
+
@object.log(:debug, 'my message')
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
it 'displays messages around the given block' do
|
|
19
|
+
@logger.should_receive(:debug).with('(start): my message').once
|
|
20
|
+
@logger.should_receive(:debug).with('(finish): my message').once
|
|
21
|
+
|
|
22
|
+
callback = mock('callback')
|
|
23
|
+
callback.should_receive(:called).and_return(:ok)
|
|
24
|
+
|
|
25
|
+
@object.log(:debug, 'my message') do
|
|
26
|
+
callback.called
|
|
27
|
+
end.should == :ok
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
it 'displays errors when block raises' do
|
|
31
|
+
@logger.should_receive(:debug).with('(start): my message').once
|
|
32
|
+
@logger.should_receive(:error).with('my message (Broken)').once
|
|
33
|
+
|
|
34
|
+
lambda do
|
|
35
|
+
@object.log(:debug, 'my message') do
|
|
36
|
+
raise StandardError, 'Broken'
|
|
37
|
+
end
|
|
38
|
+
end.should raise_error(StandardError)
|
|
39
|
+
end
|
|
40
|
+
end
|
|
41
|
+
end
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
require 'spec_helper'
|
|
2
|
+
|
|
3
|
+
describe GitWorkflow::Git do
|
|
4
|
+
before(:each) do
|
|
5
|
+
@git, @repository = Class.new, mock('Repository')
|
|
6
|
+
@git.send(:extend, GitWorkflow::Git)
|
|
7
|
+
@git.stub(:repository).and_return(@repository)
|
|
8
|
+
end
|
|
9
|
+
|
|
10
|
+
describe '.get_config_value_for!' do
|
|
11
|
+
it 'returns the value if set' do
|
|
12
|
+
@git.should_receive(:get_config_value_for).with('key').and_return('value')
|
|
13
|
+
@git.get_config_value_for!('key').should == 'value'
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
it 'raises an exception if the value is not set' do
|
|
17
|
+
@git.should_receive(:get_config_value_for).with('key').and_return(nil)
|
|
18
|
+
lambda { @git.get_config_value_for!('key') }.should raise_error(StandardError)
|
|
19
|
+
end
|
|
20
|
+
end
|
|
21
|
+
end
|
data/spec/core_functionality/4058861_git_config_returns_empty_strings_which_should_be_nil_spec.rb
ADDED
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
require 'spec_helper'
|
|
2
|
+
|
|
3
|
+
class GitWorkflow::Git::Repository
|
|
4
|
+
def self.for_testing
|
|
5
|
+
new
|
|
6
|
+
end
|
|
7
|
+
end
|
|
8
|
+
|
|
9
|
+
describe GitWorkflow::Git::Repository do
|
|
10
|
+
before(:each) do
|
|
11
|
+
@repository = described_class.for_testing
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
describe '#config_get' do
|
|
15
|
+
it 'raises ConfigError on command failure' do
|
|
16
|
+
@repository.should_receive(:execute_command).with(anything).and_raise(Execution::CommandFailure.new('command', :failure))
|
|
17
|
+
lambda { @repository.config_get('key') }.should raise_error(GitWorkflow::Git::Repository::ConfigError)
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
context 'when command succeeds' do
|
|
21
|
+
after(:each) do
|
|
22
|
+
@repository.should_receive(:execute_command).with('git config key').and_return(@value)
|
|
23
|
+
@repository.config_get('key').should == @expected
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
it 'returns the value that is set' do
|
|
27
|
+
@value = @expected = 'value'
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
it 'strips whitespace from the value' do
|
|
31
|
+
@value, @expected = ' value ', 'value'
|
|
32
|
+
end
|
|
33
|
+
|
|
34
|
+
it 'returns nil if value is empty' do
|
|
35
|
+
@value, @expected = '', nil
|
|
36
|
+
end
|
|
37
|
+
end
|
|
38
|
+
end
|
|
39
|
+
end
|
|
40
|
+
|
|
41
|
+
describe GitWorkflow::Git do
|
|
42
|
+
before(:each) do
|
|
43
|
+
@git, @repository = Class.new, mock('Repository')
|
|
44
|
+
@git.send(:extend, GitWorkflow::Git)
|
|
45
|
+
@git.stub(:repository).and_return(@repository)
|
|
46
|
+
end
|
|
47
|
+
|
|
48
|
+
describe '#get_config_value_for' do
|
|
49
|
+
it 'returns whatever is set' do
|
|
50
|
+
@repository.should_receive(:config_get).with('key').and_return(:ok)
|
|
51
|
+
@git.get_config_value_for('key').should == :ok
|
|
52
|
+
end
|
|
53
|
+
|
|
54
|
+
it 'returns nil for failure' do
|
|
55
|
+
@repository.should_receive(:config_get).with('key').and_raise(GitWorkflow::Git::Repository::ConfigError)
|
|
56
|
+
@git.get_config_value_for('key').should == nil
|
|
57
|
+
end
|
|
58
|
+
end
|
|
59
|
+
end
|
data/spec/core_functionality/4172431_add_git_workflow_setup_command_to_make_setup_easier_spec.rb
ADDED
|
@@ -0,0 +1,148 @@
|
|
|
1
|
+
require 'spec_helper'
|
|
2
|
+
|
|
3
|
+
class GitWorkflow::Commands::Setup
|
|
4
|
+
public :set_value_through
|
|
5
|
+
public :ask
|
|
6
|
+
public :choose
|
|
7
|
+
|
|
8
|
+
public :enquire_about_name
|
|
9
|
+
public :enquire_about_token
|
|
10
|
+
public :enquire_about_project_id
|
|
11
|
+
public :enquire_about_workflow
|
|
12
|
+
public :enquire_about_branches
|
|
13
|
+
public :choose_branch_convention
|
|
14
|
+
|
|
15
|
+
public :get_config_value_for
|
|
16
|
+
public :set_config_value
|
|
17
|
+
end
|
|
18
|
+
|
|
19
|
+
describe GitWorkflow::Commands::Setup do
|
|
20
|
+
before(:each) do
|
|
21
|
+
@command, @highline = described_class.new([]), mock('HighLine')
|
|
22
|
+
@command.stub(:highline).and_return(@highline)
|
|
23
|
+
|
|
24
|
+
@question = mock('Question')
|
|
25
|
+
@question.stub(:question=).with(anything)
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
describe '#execute' do
|
|
29
|
+
it 'asks the right questions' do
|
|
30
|
+
[ :name, :token, :project_id, :workflow, :branches ].each do |query|
|
|
31
|
+
@command.should_receive(:"enquire_about_#{ query }").ordered
|
|
32
|
+
end
|
|
33
|
+
@command.execute
|
|
34
|
+
end
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
describe '#ask' do
|
|
38
|
+
it 'calls through to set the value' do
|
|
39
|
+
callback = mock('callback')
|
|
40
|
+
callback.should_receive(:called)
|
|
41
|
+
|
|
42
|
+
@command.should_receive(:set_value_through).with(:ask, :setting, 'Dummy', :options).and_yield
|
|
43
|
+
@command.ask(:setting, :options) { callback.called }
|
|
44
|
+
end
|
|
45
|
+
end
|
|
46
|
+
|
|
47
|
+
describe '#choose' do
|
|
48
|
+
it 'calls through to set the value' do
|
|
49
|
+
callback = mock('callback')
|
|
50
|
+
callback.should_receive(:called)
|
|
51
|
+
|
|
52
|
+
@command.should_receive(:set_value_through).with(:choose, :setting, :options).and_yield
|
|
53
|
+
@command.choose(:setting, :options) { callback.called }
|
|
54
|
+
end
|
|
55
|
+
end
|
|
56
|
+
|
|
57
|
+
describe '#set_value_through' do
|
|
58
|
+
before(:each) do
|
|
59
|
+
@question.should_receive(:default=).with(:default)
|
|
60
|
+
|
|
61
|
+
@callback = mock('callback')
|
|
62
|
+
@callback.should_receive(:called).with(@question)
|
|
63
|
+
|
|
64
|
+
@command.should_receive(:get_config_value_for).with(:setting).and_return(:default)
|
|
65
|
+
end
|
|
66
|
+
|
|
67
|
+
it 'unspecified answer type sets value' do
|
|
68
|
+
@highline.should_receive(:question_user).with(:arg1, :arg2).and_yield(@question).and_return(:ok)
|
|
69
|
+
@command.should_receive(:set_config_value).with(:setting, :ok)
|
|
70
|
+
@command.set_value_through(:question_user, :setting, :arg1, :arg2) { |question| @callback.called(question) }
|
|
71
|
+
end
|
|
72
|
+
|
|
73
|
+
context 'when answer is optional' do
|
|
74
|
+
after(:each) do
|
|
75
|
+
@command.set_value_through(:question_user, :setting, :arg1, :arg2, :optional => true) { |question| @callback.called(question) }
|
|
76
|
+
end
|
|
77
|
+
|
|
78
|
+
it 'does not set the value if answer is blank' do
|
|
79
|
+
@highline.should_receive(:question_user).with(:arg1, :arg2).and_yield(@question).and_return('')
|
|
80
|
+
end
|
|
81
|
+
|
|
82
|
+
it 'sets the value if answer is non-blank' do
|
|
83
|
+
@highline.should_receive(:question_user).with(:arg1, :arg2).and_yield(@question).and_return('OK')
|
|
84
|
+
@command.should_receive(:set_config_value).with(:setting, 'OK')
|
|
85
|
+
end
|
|
86
|
+
end
|
|
87
|
+
end
|
|
88
|
+
|
|
89
|
+
describe '#enquire_about_name' do
|
|
90
|
+
it 'optionally prompts for the user.name' do
|
|
91
|
+
@command.should_receive(:get_config_value_for).with('user.name').and_return('John Smith')
|
|
92
|
+
@command.should_receive(:ask).with('pt.username', hash_including(:optional => true))
|
|
93
|
+
@command.enquire_about_name
|
|
94
|
+
end
|
|
95
|
+
end
|
|
96
|
+
|
|
97
|
+
describe '#enquire_about_token' do
|
|
98
|
+
it 'prompts for the pt.token' do
|
|
99
|
+
@question.should_receive(:validate=).with(/^[A-Fa-f0-9]{32}$/)
|
|
100
|
+
|
|
101
|
+
@command.should_receive(:ask).with('pt.token').and_yield(@question)
|
|
102
|
+
@command.enquire_about_token
|
|
103
|
+
end
|
|
104
|
+
end
|
|
105
|
+
|
|
106
|
+
describe '#enquire_about_project_id' do
|
|
107
|
+
it 'prompts for the pt.projectid numeric' do
|
|
108
|
+
@question.should_receive(:answer_type=).with(Integer)
|
|
109
|
+
|
|
110
|
+
@command.should_receive(:ask).with('pt.projectid').and_yield(@question)
|
|
111
|
+
@command.enquire_about_project_id
|
|
112
|
+
end
|
|
113
|
+
end
|
|
114
|
+
|
|
115
|
+
describe '#enquire_about_workflow' do
|
|
116
|
+
it 'prompts for the workflow.callbacks value' do
|
|
117
|
+
@command.should_receive(:ask).with('workflow.callbacks')
|
|
118
|
+
@command.enquire_about_workflow
|
|
119
|
+
end
|
|
120
|
+
end
|
|
121
|
+
|
|
122
|
+
describe '#enquire_about_branches' do
|
|
123
|
+
it 'prompts for branch conventions' do
|
|
124
|
+
@command.should_receive(:choose_branch_convention).with(:local)
|
|
125
|
+
@command.should_receive(:choose_branch_convention).with(:remote)
|
|
126
|
+
|
|
127
|
+
@command.enquire_about_branches
|
|
128
|
+
end
|
|
129
|
+
end
|
|
130
|
+
|
|
131
|
+
describe '#choose_branch_convention' do
|
|
132
|
+
it 'works with the correct setting' do
|
|
133
|
+
@command.should_receive(:choose).with('workflow.foobarbranchconvention')
|
|
134
|
+
@command.choose_branch_convention(:foobar)
|
|
135
|
+
end
|
|
136
|
+
|
|
137
|
+
it 'sets up the menu correctly' do
|
|
138
|
+
menu = mock('menu')
|
|
139
|
+
menu.stub(:header=).with(anything)
|
|
140
|
+
menu.should_receive(:prompt=).with(/\bfoobar\b/)
|
|
141
|
+
menu.should_receive(:menu_option).with(/number\b.+title/, '${number}_${name}')
|
|
142
|
+
menu.should_receive(:menu_option).with(/title\b.+number/, '${name}_${number}')
|
|
143
|
+
@command.should_receive(:choose).with(anything).and_yield(menu)
|
|
144
|
+
|
|
145
|
+
@command.choose_branch_convention(:foobar)
|
|
146
|
+
end
|
|
147
|
+
end
|
|
148
|
+
end
|