ghi 0.2.5 → 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/README.rdoc CHANGED
@@ -91,8 +91,36 @@ Always favor SSL by setting it:
91
91
 
92
92
  === CONTRIBUTE?
93
93
 
94
+ Running the tests should be as simple as a `bundle` and
95
+ `bundle exec spec spec`.
96
+
94
97
  ghi is not under currently under the control of any gem packaging system. To
95
98
  build, use RubyGems:
96
99
 
97
100
  % gem build ghi.gemspec
98
101
  % sudo gem install ghi*.gem
102
+
103
+
104
+ == LICENSE
105
+
106
+ (The MIT License)
107
+
108
+ (c) 2009-* Stephen Celis, stephen@stephencelis.com.
109
+
110
+ Permission is hereby granted, free of charge, to any person obtaining a copy
111
+ of this software and associated documentation files (the "Software"), to deal
112
+ in the Software without restriction, including without limitation the rights
113
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
114
+ copies of the Software, and to permit persons to whom the Software is
115
+ furnished to do so, subject to the following conditions:
116
+
117
+ The above copyright notice and this permission notice shall be included in all
118
+ copies or substantial portions of the Software.
119
+
120
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
121
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
122
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
123
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
124
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
125
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
126
+ SOFTWARE.
data/lib/ghi.rb CHANGED
@@ -1,21 +1,19 @@
1
1
  require "net/http"
2
2
  require "yaml"
3
+ YAML::ENGINE.yamler = "syck" if YAML.const_defined? :ENGINE
3
4
 
4
5
  module GHI
5
- VERSION = "0.2.4"
6
+ VERSION = "0.3.0"
6
7
 
7
8
  class << self
8
9
  def login
9
10
  return @login if defined? @login
10
11
  @login = `git config --get github.user`.chomp
11
12
  if @login.empty?
12
- begin
13
- print "Please enter your GitHub username: "
14
- @login = gets.chomp
15
- valid = user? @login
16
- warn "invalid username" unless valid
17
- end until valid
18
- `git config --global github.user #@login`
13
+ warn "Please configure your GitHub username."
14
+ puts
15
+ puts "E.g., git config --global github.user [your username]"
16
+ abort
19
17
  end
20
18
  @login
21
19
  end
@@ -24,13 +22,14 @@ module GHI
24
22
  return @token if defined? @token
25
23
  @token = `git config --get github.token`.chomp
26
24
  if @token.empty?
27
- begin
28
- print "GitHub token (https://github.com/account): "
29
- @token = gets.chomp
30
- valid = token? @token
31
- warn "invalid token for #{login}" unless valid
32
- end until valid
33
- `git config --global github.token #@token`
25
+ warn "Please configure your GitHub token."
26
+ puts
27
+ puts "E.g., git config --global github.user [your token]"
28
+ puts
29
+ puts "Find your token here: https://github.com/account/admin"
30
+ abort
31
+ elsif @token.sub!(/^!/, '')
32
+ @token = `#@token`
34
33
  end
35
34
  @token
36
35
  end
data/lib/ghi/api.rb CHANGED
@@ -1,19 +1,22 @@
1
- require "net/http"
1
+ require "net/https"
2
2
  require "yaml"
3
3
  require "cgi"
4
4
 
5
5
  class GHI::API
6
- class InvalidRequest < StandardError
6
+ class GHIError < StandardError
7
7
  end
8
8
 
9
- class InvalidConnection < StandardError
9
+ class InvalidRequest < GHIError
10
10
  end
11
11
 
12
- class ResponseError < StandardError
12
+ class InvalidConnection < GHIError
13
13
  end
14
14
 
15
- API_HOST = "github.com"
16
- API_PATH = "/api/v2/yaml/issues/:action/:user/:repo"
15
+ class ResponseError < GHIError
16
+ end
17
+
18
+ API_HOST = "github.com"
19
+ API_PATH = "/api/v2/yaml/issues/:action/:user/:repo"
17
20
 
18
21
  attr_reader :user, :repo
19
22
 
@@ -34,11 +37,21 @@ class GHI::API
34
37
  GHI::Issue.new get(:show, number)["issue"]
35
38
  end
36
39
 
40
+ def comments(number)
41
+ get(:comments, number)["comments"]
42
+ end
43
+
37
44
  def open(title, body)
45
+ if title.empty? && body.empty?
46
+ raise GHIError, "Aborting request due to empty issue."
47
+ end
38
48
  GHI::Issue.new post(:open, "title" => title, "body" => body)["issue"]
39
49
  end
40
50
 
41
51
  def edit(number, title, body)
52
+ if title.empty? && body.empty?
53
+ raise GHIError, "Aborting request due to empty issue."
54
+ end
42
55
  res = post :edit, number, "title" => title, "body" => body
43
56
  GHI::Issue.new res["issue"]
44
57
  end
@@ -60,6 +73,9 @@ class GHI::API
60
73
  end
61
74
 
62
75
  def comment(number, comment)
76
+ if comment.empty?
77
+ raise GHIError, "Aborting request due to empty comment."
78
+ end
63
79
  post(:comment, number, "comment" => comment)["comment"]
64
80
  end
65
81
 
@@ -79,7 +95,7 @@ class GHI::API
79
95
  res = YAML.load http.request(req).body
80
96
  end
81
97
 
82
- raise ResponseError, errors(res) if res["error"]
98
+ raise ResponseError, errors(res) if res["error"] || res[:error]
83
99
  res
84
100
  rescue ArgumentError, URI::InvalidURIError
85
101
  raise ResponseError, "GitHub hiccuped on your request"
@@ -99,7 +115,7 @@ class GHI::API
99
115
  res = YAML.load http.request(req).body
100
116
  end
101
117
 
102
- raise ResponseError, errors(res) if res["error"]
118
+ raise ResponseError, errors(res) if res["error"] || res[:error]
103
119
  res
104
120
  rescue ArgumentError, URI::InvalidURIError
105
121
  raise ResponseError, "GitHub hiccuped on your request"
@@ -108,6 +124,7 @@ class GHI::API
108
124
  end
109
125
 
110
126
  def errors(response)
127
+ return response[:error] if response.key? :error
111
128
  [*response["error"]].map { |e| e["error"] } * ", "
112
129
  end
113
130
 
data/lib/ghi/cli.rb CHANGED
@@ -90,12 +90,16 @@ module GHI::CLI #:nodoc:
90
90
  if verbosity
91
91
  issues.map { |i| ["=" * 79] + show_format(i) }
92
92
  else
93
- issues.map { |i| " #{i.number.to_s.rjust 3}: #{truncate(i.title, 72)}" }
93
+ issues.map { |i| " #{i.number.to_s.rjust 3}: #{truncate(i.title, 72)} #{label_format(i.labels)}" }
94
94
  end
95
95
  else
96
96
  "none"
97
97
  end
98
98
  end
99
+
100
+ def label_format(labels)
101
+ labels and labels.map {|l| "[#{l}]"}.join(' ')
102
+ end
99
103
 
100
104
  def edit_format(issue)
101
105
  l = []
@@ -122,6 +126,7 @@ module GHI::CLI #:nodoc:
122
126
  l << " number: #{issue.number}" if issue.number
123
127
  l << " state: #{issue.state}" if issue.state
124
128
  l << " title: #{indent(issue.title, 15, 0).join}" if issue.title
129
+ l << " labels: #{label_format(issue.labels)}" unless issue.labels.nil? || issue.labels.empty?
125
130
  l << " user: #{issue.user || GHI.login}"
126
131
  l << " votes: #{issue.votes}" if issue.votes
127
132
  l << " created at: #{issue.created_at}" if issue.created_at
@@ -129,6 +134,19 @@ module GHI::CLI #:nodoc:
129
134
  return l unless verbose
130
135
  l << ""
131
136
  l += indent(issue.body)[0..-2]
137
+
138
+ comments = api.comments(issue.number)
139
+ unless comments.empty?
140
+ l << "=" * 79
141
+ comments.each do |c|
142
+ l << "#{c["user"]} commented:"
143
+ l << ""
144
+ l += indent(c["body"])
145
+ l << "-" * 79
146
+ end
147
+ end
148
+
149
+ l
132
150
  end
133
151
 
134
152
  def action_format(value = nil)
@@ -143,6 +161,7 @@ module GHI::CLI #:nodoc:
143
161
  end
144
162
 
145
163
  def indent(string, level = 4, first = level)
164
+ string = string.gsub(/\n{3,}/, "\n\n")
146
165
  lines = string.scan(/.{0,#{79 - level}}(?:\s|\Z)/).map { |line|
147
166
  " " * level + line
148
167
  }
@@ -214,7 +233,7 @@ module GHI::CLI #:nodoc:
214
233
  @args, @argv = argv, argv.dup
215
234
 
216
235
  remotes = `git config --get-regexp remote\..+\.url`.split /\n/
217
- repo_expression = %r{([^:/]+)/([^/\s]+)(?:\.git)$}
236
+ repo_expression = %r{([^:/]+)/([^/\s]+?)(?:\.git)?$}
218
237
  if remote = remotes.find { |r| r.include? "github.com" }
219
238
  remote.match repo_expression
220
239
  @user, @repo = $1, $2
@@ -271,6 +290,9 @@ module GHI::CLI #:nodoc:
271
290
  rescue GHI::API::ResponseError => e
272
291
  warn "#{File.basename $0}: #{e.message} (#{user}/#{repo})"
273
292
  exit 1
293
+ rescue GHI::API::GHIError => e
294
+ warn e.message
295
+ exit 1
274
296
  end
275
297
 
276
298
  def commenting?
@@ -504,7 +526,7 @@ module GHI::CLI #:nodoc:
504
526
  comment = api.comment number, new_body
505
527
  end
506
528
  puts action_format(issue.title)
507
- puts "(comment #{comment["status"]})" if comment
529
+ puts "(commented)" if comment
508
530
  end
509
531
 
510
532
  def reopen
@@ -514,7 +536,7 @@ module GHI::CLI #:nodoc:
514
536
  comment = api.comment number, new_body
515
537
  end
516
538
  puts action_format(issue.title)
517
- puts "(comment #{comment["status"]})" if comment
539
+ puts "(commented)" if comment
518
540
  end
519
541
 
520
542
  def prepare_label
@@ -545,15 +567,15 @@ module GHI::CLI #:nodoc:
545
567
  @body ||= gets_from_editor api.show(number)
546
568
  comment = api.comment(number, body)
547
569
  delete_message
548
- puts "(comment #{comment["status"]})"
570
+ puts "(comment})"
549
571
  end
550
572
 
551
573
  def url
552
- url = "http://github.com/#{user}/#{repo}/issues"
574
+ url = "https://github.com/#{user}/#{repo}/issues"
553
575
  if number.nil?
554
576
  url << "/#{state}" unless state == :open
555
577
  else
556
- url << "#issue/#{number}"
578
+ url << "/#{number}"
557
579
  end
558
580
  defined?(Launchy) ? Launchy.open(url) : puts(url)
559
581
  end
@@ -581,7 +603,13 @@ module GHI::CLI #:nodoc:
581
603
  @action = :show
582
604
  @number ||= ($1 || arguments.shift[/\d+/]).to_i
583
605
  when "open"
584
- @action = :open
606
+ if arguments.first =~ /^\d+$/
607
+ @action = :reopen
608
+ @number ||= arguments.shift[/\d+/].to_i
609
+ else
610
+ @action = :open
611
+ @title = arguments.join(' ')
612
+ end
585
613
  when "edit"
586
614
  @action = :edit
587
615
  @number ||= arguments.shift[/\d+/].to_i
data/lib/ghi/issue.rb CHANGED
@@ -1,6 +1,6 @@
1
1
  class GHI::Issue
2
2
  attr_reader :number, :title, :body, :votes, :state, :user, :created_at,
3
- :updated_at
3
+ :updated_at, :labels
4
4
 
5
5
  def initialize(options = {})
6
6
  @number = options["number"]
@@ -11,6 +11,7 @@ class GHI::Issue
11
11
  @user = options["user"]
12
12
  @created_at = options["created_at"]
13
13
  @updated_at = options["updated_at"]
14
+ @labels = options["labels"]
14
15
  end
15
16
 
16
17
  #-
data/spec/ghi_spec.rb CHANGED
@@ -59,33 +59,4 @@ describe GHI do
59
59
  GHI.should_receive(:`).once.and_return "da39a3ee5e6b4b0d3255bfef95601890\n"
60
60
  GHI.token.should == "da39a3ee5e6b4b0d3255bfef95601890"
61
61
  end
62
-
63
- it "should approve login input" do
64
- GHI.instance_eval { instance_variable_defined?(:@login).should == false }
65
- GHI.should_receive(:`).with("git config --get github.user").
66
- and_return "\n"
67
- GHI.should_receive(:print).twice
68
- GHI.should_receive(:gets).twice.and_return "defunct\n", "defunkt\n"
69
- Net::HTTP.should_receive(:get).and_return "500: invalid: response",
70
- LOGGED_OUT_YAML
71
- GHI.should_receive(:warn).once
72
- GHI.should_receive(:`).with("git config --global github.user defunkt").
73
- and_return "\n"
74
- GHI.login.should == "defunkt"
75
- end
76
-
77
- it "should approve token input" do
78
- GHI.instance_eval { instance_variable_defined?(:@token).should == false }
79
- GHI.stub!(:login).and_return "defunkt"
80
- GHI.should_receive(:`).with("git config --get github.token").
81
- and_return "\n"
82
- GHI.should_receive(:print).twice
83
- token = "da39a3ee5e6b4b0d3255bfef95601890"
84
- GHI.should_receive(:gets).and_return "invalid\n", "#{token}\n"
85
- Net::HTTP.should_receive(:get).and_return LOGGED_OUT_YAML, LOGGED_IN_YAML
86
- GHI.should_receive(:warn).once
87
- GHI.should_receive(:`).with("git config --global github.token #{token}").
88
- and_return "\n"
89
- GHI.token.should == token
90
- end
91
62
  end
metadata CHANGED
@@ -1,38 +1,35 @@
1
- --- !ruby/object:Gem::Specification
1
+ --- !ruby/object:Gem::Specification
2
2
  name: ghi
3
- version: !ruby/object:Gem::Version
4
- prerelease: false
5
- segments:
6
- - 0
7
- - 2
8
- - 5
9
- version: 0.2.5
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.3.0
5
+ prerelease:
10
6
  platform: ruby
11
- authors:
7
+ authors:
12
8
  - Stephen Celis
13
9
  autorequire:
14
10
  bindir: bin
15
11
  cert_chain: []
16
-
17
- date: 2010-07-28 00:00:00 -05:00
18
- default_executable: ghi
19
- dependencies: []
20
-
12
+ date: 2012-01-09 00:00:00.000000000 Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ name: rspec
16
+ requirement: &70226629529100 !ruby/object:Gem::Requirement
17
+ none: false
18
+ requirements:
19
+ - - <
20
+ - !ruby/object:Gem::Version
21
+ version: '2.0'
22
+ type: :development
23
+ prerelease: false
24
+ version_requirements: *70226629529100
21
25
  description: GitHub Issues on the command line. Use your `$EDITOR`, not your browser.
22
- email:
23
- - stephen@stephencelis.com
24
- executables:
26
+ email: stephen@stephencelis.com
27
+ executables:
25
28
  - ghi
26
29
  extensions: []
27
-
28
- extra_rdoc_files:
29
- - History.rdoc
30
- - Manifest.txt
31
- - README.rdoc
32
- files:
33
- - History.rdoc
34
- - Manifest.txt
30
+ extra_rdoc_files:
35
31
  - README.rdoc
32
+ files:
36
33
  - bin/ghi
37
34
  - lib/ghi/api.rb
38
35
  - lib/ghi/cli.rb
@@ -42,38 +39,32 @@ files:
42
39
  - spec/ghi/cli_spec.rb
43
40
  - spec/ghi/issue_spec.rb
44
41
  - spec/ghi_spec.rb
45
- has_rdoc: true
42
+ - README.rdoc
46
43
  homepage: http://github.com/stephencelis/ghi
47
44
  licenses: []
48
-
49
45
  post_install_message:
50
- rdoc_options:
46
+ rdoc_options:
51
47
  - --main
52
48
  - README.rdoc
53
- require_paths:
49
+ require_paths:
54
50
  - lib
55
- required_ruby_version: !ruby/object:Gem::Requirement
51
+ required_ruby_version: !ruby/object:Gem::Requirement
56
52
  none: false
57
- requirements:
58
- - - ">="
59
- - !ruby/object:Gem::Version
60
- segments:
61
- - 0
62
- version: "0"
63
- required_rubygems_version: !ruby/object:Gem::Requirement
53
+ requirements:
54
+ - - ! '>='
55
+ - !ruby/object:Gem::Version
56
+ version: '0'
57
+ required_rubygems_version: !ruby/object:Gem::Requirement
64
58
  none: false
65
- requirements:
66
- - - ">="
67
- - !ruby/object:Gem::Version
68
- segments:
69
- - 0
70
- version: "0"
59
+ requirements:
60
+ - - ! '>='
61
+ - !ruby/object:Gem::Version
62
+ version: '0'
71
63
  requirements: []
72
-
73
- rubyforge_project: ghi
74
- rubygems_version: 1.3.7
64
+ rubyforge_project:
65
+ rubygems_version: 1.8.11
75
66
  signing_key:
76
67
  specification_version: 3
77
- summary: GitHub Issues on the command line
68
+ summary: GitHub Issues command line interface
78
69
  test_files: []
79
-
70
+ has_rdoc: true
data/History.rdoc DELETED
@@ -1,221 +0,0 @@
1
- === 0.2.5
2
-
3
- * 1 enhancement
4
-
5
- * Support for SSL with the "--ssl" flag (and "github.ssl" configuration).
6
-
7
-
8
- === 0.2.4
9
-
10
- * 1 enhancement
11
-
12
- * Detect remotes and prefer them with the "-r" flag.
13
-
14
-
15
- * 1 bugfix
16
-
17
- * Fix formatting for Ruby 1.9.1.
18
-
19
-
20
- === 0.2.3 / 2009-12-17
21
-
22
- * Minor enhancements
23
-
24
- * Better follow git's editor and pager behavior.
25
- * Accept -w and --web as alternatives to -u and --url (like git help).
26
-
27
-
28
- === 0.2.2 / 2009-11-30
29
-
30
- * 1 bugfix
31
-
32
- * Fixed Net::HTTP posts in Ruby 1.9 (params must be stringified keys).
33
-
34
-
35
- === 0.2.1 / 2009-11-29
36
-
37
- * 1 bugfix
38
-
39
- * ANSI format by word break.
40
-
41
-
42
- === 0.2.0 / 2009-11-03
43
-
44
- * Major-minor release!
45
-
46
- * Cleanup! (Better help, warnings and errors.)
47
-
48
-
49
- === 0.1.7 / 2009-08-26
50
-
51
- * 2 bugfixes
52
-
53
- * Allow dots in repo names.
54
- * Fix bug preventing invocation from non-GitHub repo directories.
55
-
56
-
57
- === 0.1.6 / 2009-08-05
58
-
59
- * 1 minor enhancement
60
-
61
- * Support for non-"origin" remotes.
62
-
63
-
64
- * 1 bugfix
65
-
66
- * Graceful offline error.
67
-
68
-
69
- === 0.1.5 / 2009-07-08
70
-
71
- * 2 bugfixes
72
-
73
- * Long titles should wrap in show/verbose issue view.
74
- * If a non-OptionParser argument fails early, re-parse when valid.
75
-
76
-
77
- === 0.1.4 / 2009-05-15
78
-
79
- * 1 minor enhancement
80
-
81
- * Minor Windows support.
82
-
83
-
84
- === 0.1.3 / 2009-05-08
85
-
86
- * 1 minor enhancement
87
-
88
- * Fix bug where `more' was being passed `less' options.
89
- * Fix scoping of commands so `ghi user/repo` can run outside of a repo
90
- directory.
91
-
92
-
93
- === 0.1.2 / 2009-05-07
94
-
95
- * 1 major enhancement
96
-
97
- * Better fallbacks. Enter `ghi open`, `ghi list closed`, `ghi search term`,
98
- `ghi show 2`, `ghi user/repo`, etc., it will try to work. Fallbacks do not
99
- accept options, though.
100
-
101
-
102
- === 0.1.1 / 2009-05-01
103
-
104
- * 3 major enhancements
105
-
106
- * Use `more' (or $GHI_PAGER) to accommodate lengthy output.
107
- * Default to "-l" if Dir.pwd is a git repo.
108
- * Accept numbered args/flags to shortcut "show" (e.g., "ghi -2", "ghi 2")
109
-
110
-
111
- * 1 minor enhancement
112
-
113
- * Update --url flag to GitHub's new convention.
114
-
115
-
116
- === 0.1.0 / 2009-04-27
117
-
118
- * 2 major enhancements
119
-
120
- * Use tempfiles when we should, the gitdir otherwise.
121
- * Now a minor!
122
-
123
-
124
- * 2 minor enhancement
125
-
126
- * Small ANSI tweaks.
127
- * Truncation fix.
128
-
129
-
130
- === 0.0.9 / 2009-04-27
131
-
132
- * 1 major enhancement
133
-
134
- * ANSI colors (honors your .gitconfig).
135
-
136
-
137
- * 1 minor enhancement
138
-
139
- * Bugfixes.
140
-
141
-
142
- === 0.0.8 / 2009-04-26
143
-
144
- * 1 major enhancement
145
-
146
- * Flag to return issues URLs.
147
-
148
-
149
- * 1 minor enhancement
150
-
151
- * Preliminary specs for top-level module and API class.
152
-
153
-
154
- === 0.0.7 / 2009-04-25
155
-
156
- * 1 major enhancement
157
-
158
- * Labels! Label and un-label at your whim.
159
-
160
-
161
- * 1 minor enhancement
162
-
163
- * Tail arguments are sometimes parsed. E.g., ghi -om "Issue message parsed".
164
-
165
-
166
- === 0.0.6 / 2009-04-25
167
-
168
- * 2 minor enhancements
169
-
170
- * Accept comments as arguments in more places.
171
- * Update error message to accommodate both issues and comments.
172
-
173
-
174
- === 0.0.5 / 2009-04-25
175
-
176
- * 3 major enhancements
177
-
178
- * Flag to claim/label issues with your GitHub username (thanks, Jamie).
179
- * Flag for commenting on issues.
180
- * Prompt for GitHub login and token if absent from gitconfig.
181
-
182
-
183
- * 1 minor enhancement
184
-
185
- * Opening issues with a title bypasses your $EDITOR.
186
-
187
-
188
- === 0.0.4 / 2009-04-24
189
-
190
- * 1 major enhancement
191
-
192
- * Cache messages created in $EDITOR.
193
-
194
-
195
- * 2 minor enhancements
196
-
197
- * Refactoring and cleanup.
198
- * Change editing messages.
199
-
200
-
201
- === 0.0.3 / 2009-04-23
202
-
203
- * 2 minor enhancements
204
-
205
- * Typo corrected.
206
- * README updated.
207
-
208
-
209
- === 0.0.2 / 2009-04-22
210
-
211
- * 1 major enhancement
212
-
213
- * Add --search flag.
214
- * Add --repo flag.
215
-
216
-
217
- === 0.0.1 / 2009-04-21
218
-
219
- * 1 major enhancement
220
-
221
- * Birthday!
data/Manifest.txt DELETED
@@ -1,14 +0,0 @@
1
- History.rdoc
2
- Manifest.txt
3
- MIT-LICENSE
4
- Rakefile
5
- README.rdoc
6
- bin/ghi
7
- lib/ghi/api.rb
8
- lib/ghi/cli.rb
9
- lib/ghi/issue.rb
10
- lib/ghi.rb
11
- spec/ghi/api_spec.rb
12
- spec/ghi/cli_spec.rb
13
- spec/ghi/issue_spec.rb
14
- spec/ghi_spec.rb