sugarjar 0.0.6 → 0.0.7

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 2820df2090fc51cb383edb67d4f4f450d659bed13da44cdf34c6fc9242084a10
4
- data.tar.gz: 6571f45c6609aa80441cea9102da98f85fef8056bfe1e7bce1d566a6ce6e1bb3
3
+ metadata.gz: 9fefe2bc9c94d95d3c869f8636bbabf433ec6196ae8d68b7ac131b4a955a882b
4
+ data.tar.gz: 5237f94836f686a0e82a8a18543b54179e7190ce874d481e59ae5fe685aa26d9
5
5
  SHA512:
6
- metadata.gz: 953d1400363c4ddddf92fb4c0f0cbbe239c60b0c19c9a47726e99c8f8bca48008079b903e9c921886a26dfe0b4c0d4495d89ae15cd32a298cfa7b5bf78317bc5
7
- data.tar.gz: bea7b4b10e735797c288b3bece8ddad975f0ebc35f264e732bdda2d583d9380f719b7f471d1df1640f1bcd6e76a3d39e36456fa18d8ede04a10de0c40355784a
6
+ metadata.gz: d8ade9a12c3ba79a5ba591123179a80aeff6db7cbd4ab48c42cc27ecd5f5f4c3bcd713b99a04654b7c28e4fca715c3f6535f9938a97f3c55fc41169791f8d6a6
7
+ data.tar.gz: cbe9733235652a2ee5d777e53eed4a0f7deb9ffdcb69b0825b89c7831c52e5317e1e854b61e038d1a27fd92c85326e560c287e9e162d3068abcd246bc0e9ee48
data/README.md CHANGED
@@ -1,6 +1,7 @@
1
1
  # SugarJar
2
2
 
3
- ![CI](https://github.com/jaymzh/sugarjar/workflows/CI/badge.svg)
3
+ [![Lint](https://github.com/jaymzh/sugarjar/workflows/Lint/badge.svg)](https://github.com/jaymzh/sugarjar/actions?query=workflow%3ALint)
4
+ [![DCO](https://github.com/jaymzh/sugarjar/workflows/DCO%20Check/badge.svg)](https://github.com/jaymzh/sugarjar/actions?query=workflow%3A%22DCO+Check%22)
4
5
  [![Gem Version](https://badge.fury.io/rb/sugarjar.svg)](https://badge.fury.io/rb/sugarjar)
5
6
 
6
7
  Welcome to SugarJar - a git/github helper. It leverages the amazing GitHub cli,
@@ -13,7 +14,7 @@ the Phabricator workflow this aims to bring to the GitHub workflow.
13
14
  In particular there are a lot of helpers for using a squash-merge workflow that
14
15
  is poorly handled by the standard toolsets.
15
16
 
16
- If you miss Mondrian or Phabrictor - this is the tool for you!
17
+ If you miss Mondrian or Phabricator - this is the tool for you!
17
18
 
18
19
  If you don't, there's a ton of useful stuff for everyone!
19
20
 
@@ -21,7 +22,7 @@ If you don't, there's a ton of useful stuff for everyone!
21
22
 
22
23
  It is common for a PR to go back and forth with a variety of nits, lint fixes,
23
24
  typos, etc. that can muddy history. So many projects will "squash and merge"
24
- when they accept a pull request. Howevet, that means `git branch -d <branch>`
25
+ when they accept a pull request. However, that means `git branch -d <branch>`
25
26
  doesn't work. Git will tell you the branch isn't fully merged. You can, of
26
27
  course `git branch -D <branch>`, but that does no safety checks at all, it
27
28
  forces the deletion.
@@ -74,7 +75,7 @@ This will:
74
75
  Note that it takes `hub`s short-names for repos. No need to specify a full URL,
75
76
  just a $org/$repo.
76
77
 
77
- Like `git clone`, `sj sclone` will accept an additional arguement as the
78
+ Like `git clone`, `sj sclone` will accept an additional argument as the
78
79
  destination directory to clone to. It will also pass any other unknown options
79
80
  to `git clone` under the hood.
80
81
 
@@ -145,7 +146,7 @@ push if any of them fail.
145
146
  ## Better push defaults
146
147
 
147
148
  In addition to running pre-push tests for you `smartpush` also picks smart
148
- defaults for push. So if you `sj spush` with no arguements, it uses the
149
+ defaults for push. So if you `sj spush` with no arguments, it uses the
149
150
  `origin` remote and the same branch name you're on as the remote branch.
150
151
 
151
152
  ## Cleaning up your own history
@@ -156,11 +157,11 @@ combination of rebases, amends and force pushes. We provide two commands here
156
157
  to help.
157
158
 
158
159
  The first is pretty straight forward and is basically just an alias: `sj
159
- amend`. It will ammend whatever you want to the most recent commit (just an
160
+ amend`. It will amend whatever you want to the most recent commit (just an
160
161
  alias for `git commit --amend`). It has a partner `qamend` (or `amendq` if you
161
162
  prefer) that will do so without prompting to update your commit message.
162
163
 
163
- So now you've rebased or amended, pushing becomes challening. You can `git push
164
+ So now you've rebased or amended, pushing becomes challenging. You can `git push
164
165
  --force`, but everyone knows that's incredibly dangerous. Is there a better
165
166
  way? There is! Git provides `git push --force-with-lease` - it checks to make
166
167
  sure you're up-to-date with the remote before forcing the push. But man that
@@ -174,7 +175,7 @@ When you want to start a new feature, you want to start developing against
174
175
  latest. That's why `sj feature` defaults to creating a branch against what we
175
176
  call "most master". That is, `upstream/master` if it exists, otherwise
176
177
  `origin/master` if that exists, otherwise `master`. You can pass in an
177
- additional arguement to base it off of something else.
178
+ additional argument to base it off of something else.
178
179
 
179
180
  ```shell
180
181
  $ git branch
data/bin/sj CHANGED
@@ -61,6 +61,20 @@ parser = OptionParser.new do |opts|
61
61
  options['log_level'] = level
62
62
  end
63
63
 
64
+ opts.on(
65
+ '--ignore-dirty',
66
+ 'Tell command that check for a dirty repo to carry on anyway.',
67
+ ) do
68
+ options['ignore_dirty'] = true
69
+ end
70
+
71
+ opts.on(
72
+ '--ignore-prerun-failure',
73
+ 'Ignore preprun failure on *push commands.',
74
+ ) do
75
+ options['ignore_prerun_failure'] = true
76
+ end
77
+
64
78
  opts.on('--version') do
65
79
  puts SugarJar::VERSION
66
80
  exit
@@ -119,6 +133,10 @@ COMMANDS:
119
133
  your account (if not already done) and then setup your remotes
120
134
  so that "origin" is your fork and "upstream" is the upstream.
121
135
 
136
+ smartpullrequest, smartpr, spr
137
+ A smart wrapper to "hub pull-request" that checks if your repo
138
+ is dirty before creating the pull request.
139
+
122
140
  smartpush, spush
123
141
  A smart wrapper to "git push" that runs whatever is defined in
124
142
  "on_push" in .sugarjar.yml, and only pushes if they succeed.
@@ -132,7 +150,7 @@ COMMANDS:
132
150
  upall
133
151
  Same as "up", but for all branches.
134
152
 
135
- verson
153
+ version
136
154
  Print the version of sugarjar, and then run 'hub version'
137
155
  to show the hub and git versions.
138
156
  COMMANDS
@@ -1,3 +1,5 @@
1
+ require 'mixlib/shellout'
2
+
1
3
  require_relative 'util'
2
4
  require_relative 'repoconfig'
3
5
  require_relative 'log'
@@ -14,6 +16,8 @@ class SugarJar
14
16
  SugarJar::Log.debug("Commands.initialize options: #{options}")
15
17
  @ghuser = options['github_user']
16
18
  @ghhost = options['github_host']
19
+ @ignore_dirty = options['ignore_dirty']
20
+ @ignore_prerun_failure = options['ignore_prerun_failure']
17
21
  @repo_config = SugarJar::RepoConfig.config
18
22
  return if options['no_change']
19
23
 
@@ -37,7 +41,10 @@ class SugarJar
37
41
  name ||= current_branch
38
42
  # rubocop:disable Style/GuardClause
39
43
  unless clean_branch(name)
40
- die("Cannot clean #{name} - there are unmerged commits")
44
+ die(
45
+ "Cannot clean #{name} - there are unmerged commits; use " +
46
+ "'git branch -D #{name}' to forcefully delete it.",
47
+ )
41
48
  end
42
49
  # rubocop:enable Style/GuardClause
43
50
  end
@@ -51,7 +58,8 @@ class SugarJar
51
58
  # rubocop:disable Style/Next
52
59
  unless clean_branch(branch)
53
60
  SugarJar::Log.info(
54
- "Skipping branch #{branch} - there are unmerged commits",
61
+ "Skipping branch #{branch} - there are unmerged commits; use " +
62
+ "'git branch -D #{branch}' to forcefully delete it.",
55
63
  )
56
64
  end
57
65
  # rubocop:enable Style/Next
@@ -139,7 +147,8 @@ class SugarJar
139
147
  # Now that we have a repo, if we have a hub host set it.
140
148
  set_hub_host if @ghhost
141
149
 
142
- org = File.basename(File.dirname(repo))
150
+ org = extract_org(repo)
151
+ SugarJar::Log.debug("Comparing org #{org} to ghuser #{@ghuser}")
143
152
  if org == @ghuser
144
153
  puts 'Cloned forked or self-owned repo. Not creating "upstream".'
145
154
  return
@@ -149,9 +158,10 @@ class SugarJar
149
158
  if s.error?
150
159
  # if the fork command failed, we already have one, so we have
151
160
  # to swap the remote names ourselves
161
+ # newer 'hub's don't fail and do the right thing...
152
162
  SugarJar::Log.info("Fork (#{@ghuser}/#{reponame}) detected.")
153
163
  hub('remote', 'rename', 'origin', 'upstream')
154
- hub('remote', 'add', 'origin', repo.gsub("#{org}/", "#{@ghuser}/"))
164
+ hub('remote', 'add', 'origin', forked_path(repo, @ghuser))
155
165
  else
156
166
  SugarJar::Log.info("Forked #{reponame} to #{@ghuser}")
157
167
  end
@@ -162,38 +172,25 @@ class SugarJar
162
172
  alias sclone smartclone
163
173
 
164
174
  def lint
175
+ assert_in_repo
165
176
  exit(1) unless run_check('lint')
166
177
  end
167
178
 
168
179
  def unit
180
+ assert_in_repo
169
181
  exit(1) unless run_check('unit')
170
182
  end
171
183
 
172
184
  def smartpush(remote = nil, branch = nil)
173
- unless remote && branch
174
- remote ||= 'origin'
175
- branch ||= current_branch
176
- end
177
-
178
- if run_prepush
179
- puts hub('push', remote, branch).stderr
180
- else
181
- SugarJar::Log.error('Pre-push checks failed. Not pushing.')
182
- end
185
+ assert_in_repo
186
+ _smartpush(remote, branch, false)
183
187
  end
184
188
 
185
189
  alias spush smartpush
186
190
 
187
191
  def forcepush(remote = nil, branch = nil)
188
- unless remote && branch
189
- remote ||= 'origin'
190
- branch ||= current_branch
191
- end
192
- if run_prepush
193
- puts hub('push', '--force-with-lease', remote, branch).stderr
194
- else
195
- SugarJar::Log.error('Pre-push checks failed. Not pushing.')
196
- end
192
+ assert_in_repo
193
+ _smartpush(remote, branch, true)
197
194
  end
198
195
 
199
196
  alias fpush forcepush
@@ -203,8 +200,86 @@ class SugarJar
203
200
  puts hub('version').stdout
204
201
  end
205
202
 
203
+ def smartpullrequest
204
+ assert_in_repo
205
+ if dirty?
206
+ SugarJar::Log.warn(
207
+ 'Your repo is dirty, so I am not going to create a pull request. ' +
208
+ 'You should commit or amend and push it to your remote first.',
209
+ )
210
+ exit(1)
211
+ end
212
+ system(which('hub'), 'pull-request')
213
+ end
214
+
215
+ alias spr smartpullrequest
216
+ alias smartpr smartpullrequest
217
+
206
218
  private
207
219
 
220
+ def _smartpush(remote, branch, force)
221
+ unless remote && branch
222
+ remote ||= 'origin'
223
+ branch ||= current_branch
224
+ end
225
+
226
+ if dirty?
227
+ if @ignore_dirty
228
+ SugarJar::Log.warn(
229
+ 'Your repo is dirty, but --ignore-dirty was specified, so ' +
230
+ 'carrying on anyway.',
231
+ )
232
+ else
233
+ SugarJar::Log.error(
234
+ 'Your repo is dirty, so I am not going to push. Please commit ' +
235
+ 'or amend first.',
236
+ )
237
+ exit(1)
238
+ end
239
+ end
240
+
241
+ unless run_prepush
242
+ if @ignore_prerun_failure
243
+ SugarJar::Log.warn(
244
+ 'Pre-push checks failed, but --ignore-prerun-failure was ' +
245
+ 'specified, so carrying on anyway',
246
+ )
247
+ else
248
+ SugarJar::Log.error('Pre-push checks failed. Not pushing.')
249
+ exit(1)
250
+ end
251
+ end
252
+
253
+ args = ['push', remote, branch]
254
+ args << '--force-with-lease' if force
255
+ puts hub(*args).stderr
256
+ end
257
+
258
+ def dirty?
259
+ s = hub_nofail('diff', '--quiet')
260
+ s.error?
261
+ end
262
+
263
+ def extract_org(path)
264
+ if path.start_with?('http')
265
+ File.basename(File.dirname(path))
266
+ elsif path.start_with?('git@')
267
+ path.split(':')[1].split('/')[0]
268
+ else
269
+ # assume they passed in a hub-friendly name
270
+ path.split('/').first
271
+ end
272
+ end
273
+
274
+ def forked_path(path, username)
275
+ repo = if path.start_with?('http', 'git@')
276
+ File.basename(path)
277
+ else
278
+ "#{File.basename(path)}.git"
279
+ end
280
+ "git@github.com:#{username}/#{repo}"
281
+ end
282
+
208
283
  def set_hub_host
209
284
  return unless in_repo
210
285
 
@@ -213,7 +288,7 @@ class SugarJar
213
288
  SugarJar::Log.info("Setting repo hub.host = #{@ghhost}")
214
289
  else
215
290
  current = s.stdout
216
- if current == @ghost
291
+ if current == @ghhost
217
292
  SugarJar::Log.debug('Repo hub.host already set correctly')
218
293
  else
219
294
  # Even though we have an explicit config, in most cases, it
@@ -13,7 +13,7 @@ class SugarJar
13
13
  def self._find_ordered_files
14
14
  [
15
15
  '/etc/sugarjar/config.yaml',
16
- "#{ENV['HOME']}/.config/sugarjar/config.yaml"
16
+ "#{ENV['HOME']}/.config/sugarjar/config.yaml",
17
17
  ].select { |f| File.exist?(f) }
18
18
  end
19
19
 
@@ -29,23 +29,46 @@ class SugarJar
29
29
  def hub_nofail(*args)
30
30
  SugarJar::Log.trace("Running: hub #{args.join(' ')}")
31
31
  s = Mixlib::ShellOut.new([which('hub')] + args).run_command
32
- # depending on hub version and possibly other things, STDERR
33
- # is either "Requires authentication" or "Must authenticate"
34
- if s.error? && s.stderr =~ /^(Must|Requires) authenticat/
35
- SugarJar::Log.info(
36
- 'Hub was run but no github token exists. Will run "hub api user" ' +
37
- "to force\nhub to authenticate...",
38
- )
39
- unless system(which('hub'), 'api', 'user')
40
- SugarJar::Log.fatal(
41
- 'That failed, I will bail out. Hub needs to get a github ' +
42
- 'token. Try running "hub api user" (will list info about ' +
43
- 'your account) and try this again when that works.',
32
+ if s.error?
33
+ # depending on hub version and possibly other things, STDERR
34
+ # is either "Requires authentication" or "Must authenticate"
35
+ case s.stderr
36
+ when /^(Must|Requires) authenticat/
37
+ SugarJar::Log.info(
38
+ 'Hub was run but no github token exists. Will run "hub api user" ' +
39
+ "to force\nhub to authenticate...",
44
40
  )
45
- exit(1)
41
+ unless system(which('hub'), 'api', 'user')
42
+ SugarJar::Log.fatal(
43
+ 'That failed, I will bail out. Hub needs to get a github ' +
44
+ 'token. Try running "hub api user" (will list info about ' +
45
+ 'your account) and try this again when that works.',
46
+ )
47
+ exit(1)
48
+ end
49
+ SugarJar::Log.info('Re-running original hub command...')
50
+ s = Mixlib::ShellOut.new([which('hub')] + args).run_command
51
+ when /^fatal: could not read Username/
52
+ # On http(s) URLs, git may prompt for username/passwd
53
+ SugarJar::Log.info(
54
+ 'Hub was run but git prompted for authentication. This probably ' +
55
+ "means you have\nused an http repo URL instead of an ssh one. It " +
56
+ "is recommended you reclone\nusing 'sj sclone' to setup your " +
57
+ "remotes properly. However, in the meantime,\nwe'll go ahead " +
58
+ "and re-run the command in a shell so you can type in the\n" +
59
+ 'credentials.',
60
+ )
61
+ unless system(which('hub'), *args)
62
+ SugarJar::Log.fatal(
63
+ 'That failed, I will bail out. You can either manually change ' +
64
+ 'your remotes, or simply create a fresh clone with ' +
65
+ '"sj smartclone".',
66
+ )
67
+ exit(1)
68
+ end
69
+ SugarJar::Log.info('Re-running original hub command...')
70
+ s = Mixlib::ShellOut.new([which('hub')] + args).run_command
46
71
  end
47
- SugarJar::Log.info('Re-running original hub command...')
48
- s = Mixlib::ShellOut.new([which('hub')] + args).run_command
49
72
  end
50
73
  s
51
74
  end
@@ -1,3 +1,3 @@
1
1
  class SugarJar
2
- VERSION = '0.0.6'.freeze
2
+ VERSION = '0.0.7'.freeze
3
3
  end
@@ -8,6 +8,7 @@ Gem::Specification.new do |spec|
8
8
  spec.email = ['phil@ipom.com']
9
9
  spec.license = 'Apache-2.0'
10
10
  spec.homepage = 'https://github.com/jaymzh/sugarjar'
11
+ spec.required_ruby_version = '>= 2.6.0'
11
12
  docs = %w{README.md LICENSE Gemfile sugarjar.gemspec}
12
13
  spec.extra_rdoc_files = docs
13
14
  spec.executables << 'sj'
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: sugarjar
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.6
4
+ version: 0.0.7
5
5
  platform: ruby
6
6
  authors:
7
7
  - Phil Dibowitz
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2020-07-06 00:00:00.000000000 Z
11
+ date: 2020-11-24 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: mixlib-log
@@ -73,7 +73,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
73
73
  requirements:
74
74
  - - ">="
75
75
  - !ruby/object:Gem::Version
76
- version: '0'
76
+ version: 2.6.0
77
77
  required_rubygems_version: !ruby/object:Gem::Requirement
78
78
  requirements:
79
79
  - - ">="