twig 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,126 @@
1
+ require 'spec_helper'
2
+
3
+ describe Twig::Options do
4
+ before :each do
5
+ @twig = Twig.new
6
+ end
7
+
8
+ describe '#read_config_file!' do
9
+ before :each do
10
+ File.should_receive(:expand_path).with(Twig::CONFIG_FILE).
11
+ and_return(Twig::CONFIG_FILE)
12
+ end
13
+
14
+ it 'reads and sets a single option' do
15
+ @twig.stub(:branch_names => ['test'])
16
+ file = double('file')
17
+ File.should_receive(:readable?).with(Twig::CONFIG_FILE).and_return(true)
18
+ File.should_receive(:open).with(Twig::CONFIG_FILE).and_yield(file)
19
+ file.should_receive(:read).and_return(%{
20
+ branch: test
21
+ }.gsub(/^\s+/, ''))
22
+ @twig.options[:branch].should be_nil # Precondition
23
+
24
+ @twig.read_config_file!
25
+
26
+ @twig.options[:branch].should == 'test'
27
+ end
28
+
29
+ it 'reads and sets multiple options' do
30
+ @twig.stub(:branch_names => ['test'])
31
+ file = double('file')
32
+ File.should_receive(:readable?).with(Twig::CONFIG_FILE).and_return(true)
33
+ File.should_receive(:open).with(Twig::CONFIG_FILE).and_yield(file)
34
+ file.should_receive(:read).and_return(%{
35
+ branch: test
36
+ except-branch: test-except
37
+ only-branch: test-only
38
+ max-days-old: 30.5
39
+ }.gsub(/^\s+/, ''))
40
+ @twig.options[:branch].should be_nil # Precondition
41
+ @twig.options[:branch_except].should be_nil # Precondition
42
+ @twig.options[:branch_only].should be_nil # Precondition
43
+ @twig.options[:max_days_old].should be_nil # Precondition
44
+
45
+ @twig.read_config_file!
46
+
47
+ @twig.options[:branch].should == 'test'
48
+ @twig.options[:branch_except].should == /test-except/
49
+ @twig.options[:branch_only].should == /test-only/
50
+ @twig.options[:max_days_old].should == 30.5
51
+ end
52
+
53
+ it 'fails gracefully if the config file is not readable' do
54
+ File.should_receive(:readable?).with(Twig::CONFIG_FILE).and_return(false)
55
+ lambda { @twig.read_config_file! }.should_not raise_exception
56
+ end
57
+ end
58
+
59
+ describe '#set_option' do
60
+ context 'when setting a :branch option' do
61
+ before :each do
62
+ @twig.options[:branch].should be_nil # Precondition
63
+ end
64
+
65
+ it 'succeeds' do
66
+ @twig.should_receive(:branch_names).and_return(%[foo bar])
67
+ @twig.set_option(:branch, 'foo')
68
+ @twig.options[:branch].should == 'foo'
69
+ end
70
+
71
+ it 'fails if the branch is unknown' do
72
+ @twig.should_receive(:branch_names).and_return([])
73
+ @twig.should_receive(:abort)
74
+
75
+ @twig.set_option(:branch, 'foo')
76
+
77
+ @twig.options[:branch].should be_nil
78
+ end
79
+ end
80
+
81
+ it 'sets a :branch_except option' do
82
+ @twig.options[:branch_except].should be_nil # Precondition
83
+ @twig.set_option(:branch_except, 'unwanted_prefix_')
84
+ @twig.options[:branch_except].should == /unwanted_prefix_/
85
+ end
86
+
87
+ it 'sets a :branch_only option' do
88
+ @twig.options[:branch_only].should be_nil # Precondition
89
+ @twig.set_option(:branch_only, 'important_prefix_')
90
+ @twig.options[:branch_only].should == /important_prefix_/
91
+ end
92
+
93
+ context 'when setting a :max_days_old option' do
94
+ before :each do
95
+ @twig.options[:max_days_old].should be_nil # Precondition
96
+ end
97
+
98
+ it 'succeeds' do
99
+ @twig.set_option(:max_days_old, 1)
100
+ @twig.options[:max_days_old].should == 1
101
+ end
102
+
103
+ it 'fails if the option is not numeric' do
104
+ @twig.should_receive(:abort)
105
+ @twig.set_option(:max_days_old, 'blargh')
106
+ @twig.options[:max_days_old].should be_nil
107
+ end
108
+ end
109
+
110
+ it 'sets an :unset_property option' do
111
+ @twig.options[:unset_property].should be_nil # Precondition
112
+ @twig.set_option(:unset_property, 'unwanted_property')
113
+ @twig.options[:unset_property].should == 'unwanted_property'
114
+ end
115
+ end
116
+
117
+ describe '#unset_option' do
118
+ it 'unsets an option' do
119
+ @twig.set_option(:max_days_old, 1)
120
+ @twig.options[:max_days_old].should == 1 # Precondition
121
+
122
+ @twig.unset_option(:max_days_old)
123
+ @twig.options[:max_days_old].should be_nil
124
+ end
125
+ end
126
+ end
@@ -0,0 +1,16 @@
1
+ require 'spec_helper'
2
+
3
+ describe Twig::Util do
4
+ describe '.numeric?' do
5
+ it 'returns true if an object is numeric' do
6
+ Twig::Util.numeric?(1).should be_true
7
+ Twig::Util.numeric?('1').should be_true
8
+ end
9
+
10
+ it 'returns false if an object is not numeric' do
11
+ Twig::Util.numeric?('x').should be_false
12
+ Twig::Util.numeric?([]).should be_false
13
+ Twig::Util.numeric?({}).should be_false
14
+ end
15
+ end
16
+ end
data/spec/twig_spec.rb ADDED
@@ -0,0 +1,220 @@
1
+ require 'spec_helper'
2
+
3
+ describe Twig do
4
+ describe '#initialize' do
5
+ it 'creates a Twig instance' do
6
+ twig = Twig.new
7
+ twig.options.should == {}
8
+ end
9
+
10
+ it 'creates a Twig instance with arbitrary options' do
11
+ options = {:foo => 'bar'}
12
+ twig = Twig.new(options)
13
+
14
+ twig.options.should == options
15
+ end
16
+ end
17
+
18
+ describe '#current_branch_name' do
19
+ it 'returns the current branch name' do
20
+ twig = Twig.new
21
+ branch_name = 'fix_all_the_things'
22
+ Twig.should_receive(:run).
23
+ with('git symbolic-ref -q HEAD').
24
+ once. # Should memoize
25
+ and_return(Twig::REF_PREFIX + branch_name)
26
+
27
+ 2.times { twig.current_branch_name.should == branch_name }
28
+ end
29
+ end
30
+
31
+ describe '#all_branches' do
32
+ before :each do
33
+ @branch_names = %w[
34
+ fix_some_of_the_things
35
+ fix_some_other_of_the_things
36
+ fix_nothing
37
+ ]
38
+ branch_refs = @branch_names.map { |name| Twig::REF_PREFIX + name }
39
+ @commit_time_strings = ['2001-01-01', '2002-02-02', '2003-03-03' ]
40
+ @commit_time_agos = ['111 days ago', '222 days ago', '333 days ago']
41
+ @command =
42
+ %{git for-each-ref #{Twig::REF_PREFIX} --format="#{Twig::REF_FORMAT}"}
43
+
44
+ @branch_tuples = (0..2).map do |i|
45
+ "#{branch_refs[i]},#{@commit_time_strings[i]},#{@commit_time_agos[i]}"
46
+ end.join("\n")
47
+ end
48
+
49
+ it 'returns an array of branches' do
50
+ Twig.should_receive(:run).with(@command).and_return(@branch_tuples)
51
+ twig = Twig.new
52
+
53
+ branches = twig.all_branches
54
+
55
+ branches[0].name.should == @branch_names[0]
56
+ branches[0].last_commit_time.to_s.
57
+ should =~ %r{#{@commit_time_strings[0]} .* \(111d ago\)}
58
+ branches[1].name.should == @branch_names[1]
59
+ branches[1].last_commit_time.to_s.
60
+ should =~ %r{#{@commit_time_strings[1]} .* \(222d ago\)}
61
+ branches[2].name.should == @branch_names[2]
62
+ branches[2].last_commit_time.to_s.
63
+ should =~ %r{#{@commit_time_strings[2]} .* \(333d ago\)}
64
+ end
65
+
66
+ it 'memoizes the result' do
67
+ Twig.should_receive(:run).with(@command).once.and_return(@branch_tuples)
68
+ twig = Twig.new
69
+
70
+ 2.times { twig.all_branches }
71
+ end
72
+ end
73
+
74
+ describe '#branches' do
75
+ before :each do
76
+ @twig = Twig.new
77
+ branch_names = %w[
78
+ fix_some_of_the_things
79
+ fix_some_other_of_the_things
80
+ fix_nothing
81
+ ]
82
+ commit_times = [
83
+ Twig::CommitTime.new(Time.now - 86400 * 10, '10 days ago'),
84
+ Twig::CommitTime.new(Time.now - 86400 * 20, '20 days ago'),
85
+ Twig::CommitTime.new(Time.now - 86400 * 30, '30 days ago')
86
+ ]
87
+ @branches = [
88
+ Twig::Branch.new(branch_names[0], :last_commit_time => commit_times[0]),
89
+ Twig::Branch.new(branch_names[1], :last_commit_time => commit_times[1]),
90
+ Twig::Branch.new(branch_names[2], :last_commit_time => commit_times[2])
91
+ ]
92
+ @twig.stub(:all_branches => @branches)
93
+ end
94
+
95
+ it 'returns all branches' do
96
+ @twig.branches.should == @branches
97
+ end
98
+
99
+ it 'returns only branches matching a name pattern' do
100
+ @twig.set_option(:branch_only, /fix_some/)
101
+ @twig.branches.map { |branch| branch.name }.
102
+ should == [@branches[0].name, @branches[1].name]
103
+ end
104
+
105
+ it 'returns all branches except those matching a name pattern' do
106
+ @twig.set_option(:branch_except, /fix_some/)
107
+ @twig.branches.map { |branch| branch.name }.should == [@branches[2].name]
108
+ end
109
+
110
+ it 'returns only branches below a certain age' do
111
+ @twig.set_option(:max_days_old, 25)
112
+ @twig.branches.map { |branch| branch.name }.
113
+ should == [@branches[0].name, @branches[1].name]
114
+ end
115
+ end
116
+
117
+ describe '#branch_names' do
118
+ it 'returns an array of branch names' do
119
+ twig = Twig.new
120
+ branch_names = %w[foo bar baz]
121
+ branches = branch_names.map { |name| Twig::Branch.new(name) }
122
+ twig.should_receive(:branches).and_return(branches)
123
+
124
+ twig.branch_names.should == branch_names
125
+ end
126
+ end
127
+
128
+ describe '#list_branches' do
129
+ before :each do
130
+ @twig = Twig.new
131
+ @list_headers = '[branch list headers]'
132
+ commit_times = [
133
+ Twig::CommitTime.new(Time.now, '111 days ago'),
134
+ Twig::CommitTime.new(Time.now, '222 days ago')
135
+ ]
136
+ commit_times[0].stub(:to_i => 2000_01_01 )
137
+ commit_times[0].stub(:to_s =>'2000-01-01')
138
+ commit_times[1].stub(:to_i => 2000_01_02 )
139
+ commit_times[1].stub(:to_s =>'2000-01-02')
140
+ @branches = [
141
+ Twig::Branch.new('foo', :last_commit_time => commit_times[0]),
142
+ Twig::Branch.new('foo', :last_commit_time => commit_times[1])
143
+ ]
144
+ @branch_lines = ['[foo line]', '[bar line]']
145
+ end
146
+
147
+ it 'returns a list of branches, most recently modified first' do
148
+ @twig.should_receive(:branches).at_least(:once).and_return(@branches)
149
+ @twig.should_receive(:branch_list_headers).and_return(@list_headers)
150
+ @twig.should_receive(:branch_list_line).with(@branches[0]).
151
+ and_return(@branch_lines[0])
152
+ @twig.should_receive(:branch_list_line).with(@branches[1]).
153
+ and_return(@branch_lines[1])
154
+ result = @twig.list_branches
155
+
156
+ result.should == "\n" + @list_headers +
157
+ @branch_lines[1] + "\n" + @branch_lines[0]
158
+ end
159
+
160
+ it 'returns a message if all branches were filtered out by options' do
161
+ @twig.stub(:all_branches => %[foo bar])
162
+ @twig.stub(:branches => [])
163
+
164
+ @twig.list_branches.should include(
165
+ 'There are no branches matching your selected options'
166
+ )
167
+ end
168
+
169
+ it 'returns a message if the repo has no branches' do
170
+ @twig.stub(:all_branches => [])
171
+ @twig.stub(:branches => [])
172
+
173
+ @twig.list_branches.should include('This repository has no branches')
174
+ end
175
+ end
176
+
177
+ describe '#get_branch_property' do
178
+ before :each do
179
+ @twig = Twig.new
180
+ @branch = Twig::Branch.new('test')
181
+ end
182
+
183
+ it 'calls `Twig::Branch#get_property`' do
184
+ property_name = 'foo'
185
+ property_value = 'bar'
186
+ Twig::Branch.should_receive(:new).with(@branch.name).and_return(@branch)
187
+ @branch.should_receive(:get_property).with(property_name).
188
+ and_return(property_value)
189
+
190
+ result = @twig.get_branch_property(@branch.name, property_name)
191
+ result.should == property_value
192
+ end
193
+ end
194
+
195
+ describe '#set_branch_property' do
196
+ it 'calls `Twig::Branch#set_property`' do
197
+ twig = Twig.new
198
+ branch = Twig::Branch.new('test')
199
+ property_name = 'foo'
200
+ property_value = 'bar'
201
+ Twig::Branch.should_receive(:new).with(branch.name).and_return(branch)
202
+ branch.should_receive(:set_property).with(property_name, property_value)
203
+
204
+ twig.set_branch_property(branch.name, property_name, property_value)
205
+ end
206
+ end
207
+
208
+ describe '#unset_branch_property' do
209
+ it 'calls `Twig::Branch#unset_property`' do
210
+ twig = Twig.new
211
+ branch = Twig::Branch.new('test')
212
+ property_name = 'foo'
213
+ Twig::Branch.should_receive(:new).with(branch.name).and_return(branch)
214
+ branch.should_receive(:unset_property).with(property_name)
215
+
216
+ twig.unset_branch_property(branch.name, property_name)
217
+ end
218
+ end
219
+
220
+ end
data/twig.gemspec ADDED
@@ -0,0 +1,38 @@
1
+ # -*- encoding: utf-8 -*-
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+ require 'twig/version'
5
+
6
+ Gem::Specification.new do |spec|
7
+ spec.name = 'twig'
8
+ spec.version = Twig::VERSION
9
+ spec.date = '2012-12-13'
10
+ spec.authors = ['Ron DeVera']
11
+ spec.email = ["hello@rondevera.com"]
12
+ spec.homepage = 'https://github.com/rondevera/twig'
13
+ spec.summary = %{Track progress on your Git branches.}
14
+ spec.description =
15
+ 'Twig is a command-line tool for tracking progress on your Git ' <<
16
+ 'branches, remembering ticket ids for each branch, and more. Twig ' <<
17
+ 'supports subcommands for managing branches however you want.'
18
+ spec.post_install_message =
19
+ "\n**************************************************************" <<
20
+ "\n* *" <<
21
+ "\n* Welcome to Twig! *" <<
22
+ "\n* *" <<
23
+ "\n* To get started, run `twig` to list your Git branches, and *" <<
24
+ "\n* `twig --help` for more info. *" <<
25
+ "\n* *" <<
26
+ "\n**************************************************************" <<
27
+ "\n\n"
28
+
29
+ spec.files = `git ls-files`.split($/)
30
+ spec.executables = spec.files.grep(%r{^bin/}).map { |file| File.basename(file) }
31
+ spec.require_paths = ['lib']
32
+ spec.test_files = spec.files.grep(%r{^spec/})
33
+
34
+ spec.required_ruby_version = '>= 1.8.7'
35
+ spec.add_runtime_dependency 'json', '~> 1.7.5'
36
+ spec.add_development_dependency 'rake', '~> 0.9.2'
37
+ spec.add_development_dependency 'rspec', '~> 2.11.0'
38
+ end
metadata ADDED
@@ -0,0 +1,166 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: twig
3
+ version: !ruby/object:Gem::Version
4
+ hash: 23
5
+ prerelease:
6
+ segments:
7
+ - 1
8
+ - 0
9
+ - 0
10
+ version: 1.0.0
11
+ platform: ruby
12
+ authors:
13
+ - Ron DeVera
14
+ autorequire:
15
+ bindir: bin
16
+ cert_chain: []
17
+
18
+ date: 2012-12-13 00:00:00 -08:00
19
+ default_executable:
20
+ dependencies:
21
+ - !ruby/object:Gem::Dependency
22
+ name: json
23
+ prerelease: false
24
+ requirement: &id001 !ruby/object:Gem::Requirement
25
+ none: false
26
+ requirements:
27
+ - - ~>
28
+ - !ruby/object:Gem::Version
29
+ hash: 1
30
+ segments:
31
+ - 1
32
+ - 7
33
+ - 5
34
+ version: 1.7.5
35
+ type: :runtime
36
+ version_requirements: *id001
37
+ - !ruby/object:Gem::Dependency
38
+ name: rake
39
+ prerelease: false
40
+ requirement: &id002 !ruby/object:Gem::Requirement
41
+ none: false
42
+ requirements:
43
+ - - ~>
44
+ - !ruby/object:Gem::Version
45
+ hash: 63
46
+ segments:
47
+ - 0
48
+ - 9
49
+ - 2
50
+ version: 0.9.2
51
+ type: :development
52
+ version_requirements: *id002
53
+ - !ruby/object:Gem::Dependency
54
+ name: rspec
55
+ prerelease: false
56
+ requirement: &id003 !ruby/object:Gem::Requirement
57
+ none: false
58
+ requirements:
59
+ - - ~>
60
+ - !ruby/object:Gem::Version
61
+ hash: 35
62
+ segments:
63
+ - 2
64
+ - 11
65
+ - 0
66
+ version: 2.11.0
67
+ type: :development
68
+ version_requirements: *id003
69
+ description: Twig is a command-line tool for tracking progress on your Git branches, remembering ticket ids for each branch, and more. Twig supports subcommands for managing branches however you want.
70
+ email:
71
+ - hello@rondevera.com
72
+ executables:
73
+ - twig
74
+ - twig-gh-open
75
+ - twig-gh-update
76
+ - twig-help
77
+ extensions: []
78
+
79
+ extra_rdoc_files: []
80
+
81
+ files:
82
+ - .gitignore
83
+ - .rvmrc
84
+ - CONTRIBUTING.md
85
+ - Gemfile
86
+ - HISTORY.md
87
+ - LICENSE.md
88
+ - README.md
89
+ - Rakefile
90
+ - bin/twig
91
+ - bin/twig-gh-open
92
+ - bin/twig-gh-update
93
+ - bin/twig-help
94
+ - install
95
+ - lib/twig.rb
96
+ - lib/twig/branch.rb
97
+ - lib/twig/cli.rb
98
+ - lib/twig/commit_time.rb
99
+ - lib/twig/display.rb
100
+ - lib/twig/options.rb
101
+ - lib/twig/util.rb
102
+ - lib/twig/version.rb
103
+ - spec/spec_helper.rb
104
+ - spec/twig/branch_spec.rb
105
+ - spec/twig/cli_spec.rb
106
+ - spec/twig/commit_time_spec.rb
107
+ - spec/twig/display_spec.rb
108
+ - spec/twig/options_spec.rb
109
+ - spec/twig/util_spec.rb
110
+ - spec/twig_spec.rb
111
+ - twig.gemspec
112
+ has_rdoc: true
113
+ homepage: https://github.com/rondevera/twig
114
+ licenses: []
115
+
116
+ post_install_message: |+
117
+
118
+ **************************************************************
119
+ * *
120
+ * Welcome to Twig! *
121
+ * *
122
+ * To get started, run `twig` to list your Git branches, and *
123
+ * `twig --help` for more info. *
124
+ * *
125
+ **************************************************************
126
+
127
+ rdoc_options: []
128
+
129
+ require_paths:
130
+ - lib
131
+ required_ruby_version: !ruby/object:Gem::Requirement
132
+ none: false
133
+ requirements:
134
+ - - ">="
135
+ - !ruby/object:Gem::Version
136
+ hash: 57
137
+ segments:
138
+ - 1
139
+ - 8
140
+ - 7
141
+ version: 1.8.7
142
+ required_rubygems_version: !ruby/object:Gem::Requirement
143
+ none: false
144
+ requirements:
145
+ - - ">="
146
+ - !ruby/object:Gem::Version
147
+ hash: 3
148
+ segments:
149
+ - 0
150
+ version: "0"
151
+ requirements: []
152
+
153
+ rubyforge_project:
154
+ rubygems_version: 1.5.2
155
+ signing_key:
156
+ specification_version: 3
157
+ summary: Track progress on your Git branches.
158
+ test_files:
159
+ - spec/spec_helper.rb
160
+ - spec/twig/branch_spec.rb
161
+ - spec/twig/cli_spec.rb
162
+ - spec/twig/commit_time_spec.rb
163
+ - spec/twig/display_spec.rb
164
+ - spec/twig/options_spec.rb
165
+ - spec/twig/util_spec.rb
166
+ - spec/twig_spec.rb