Module: GitHelpers::GitExtraInfos

Included in:
GitDir
Defined in:
lib/git_helpers/extra_helpers.rb

Overview

various helpers

Instance Method Summary collapse

Instance Method Details

#aliasesObject

inspired by visionmedia//git-alias



281
282
283
284
285
286
287
# File 'lib/git_helpers/extra_helpers.rb', line 281

def aliases
  with_dir do
    %x/git config --get-regexp 'alias.*'/.each_line.map do |l|
      puts l.sub(/^alias\./,"").sub(/ /," = ")
    end
  end
end

#commit_children(*commits) ⇒ Object



219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
# File 'lib/git_helpers/extra_helpers.rb', line 219

def commit_children(*commits)
  r={}
  with_dir do
    commits.each do |commit|
      commit_id=%x/git rev-parse "#{commit}^0"/.chomp #dereference tags
      %x/git rev-list --all --not #{commit_id}^@ --children/.each_line do |l|
        if l=~/^#{commit_id}/
          _commit, *children=l.chomp.split
          described=children.map {|c| %x/git describe --always #{c}/.chomp}
          r[commit]||=[]
          r[commit]+=described
        end
      end
    end
  end
  r
end

#commits_by_files(*files) ⇒ Object

Inspired by the script git-effort from visionmedia



262
263
264
265
266
267
268
269
270
271
272
# File 'lib/git_helpers/extra_helpers.rb', line 262

def commits_by_files(*files)
  r={}
  files=all_files if files.empty?
  with_dir do
    files.each do |file|
      dates=%x/git log #{DefaultLogOptions} --pretty='format: %ad' --date=short -- "#{file}"/.each_line.map {|l| l.chomp}
      r[file]={commits: dates.length, active: dates.uniq.length}
    end
  end
  r
end

#log_commits_by_files(logopts = nil) ⇒ Object

number of commits modifying each file (look in the logs) Inspired by the script git-churn, written by Corey Haines # Scriptified by Gary Bernhardt



244
245
246
247
248
249
250
251
252
253
254
# File 'lib/git_helpers/extra_helpers.rb', line 244

def log_commits_by_files(logopts=nil)
  r={}
  with_dir do
    files=%x/git log #{DefaultLogOptions} --name-only --format="" #{logopts}/.each_line.map {|l| l.chomp!}
    uniq=files.uniq
    uniq.each do |file|
      r[file]=files.count(file)
    end
  end
  r
end

#neck(*args, **opts) ⇒ Object

inspired by git-neck from https://github.com/cypher/dotfiles



341
342
343
344
345
346
347
348
349
350
351
352
# File 'lib/git_helpers/extra_helpers.rb', line 341

def neck(*args, **opts)
  with_dir do
    commit=`git rev-parse --revs-only --default HEAD #{args.shelljoin}`.chomp
    log_opts=`git rev-parse --flags --no-revs #{args.shelljoin}`.chomp
    hash=`git rev-parse #{commit.shellescape}`.chomp
    merges=trails(commit, **opts)
    merges.delete(hash) #todo: only delete if we are the only tip
    merges.delete(:disjoint)
    system("git --no-pager -c color.ui=always log --pretty=summary #{log_opts} #{merges.keys.map {|mb| "^#{mb}"}.join(" ")} #{commit}")
    puts
  end
end

#output_all_trails(*args, **opts) ⇒ Object



307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
# File 'lib/git_helpers/extra_helpers.rb', line 307

def output_all_trails(*args, **opts)
  args.each do |commit|
    trails(commit, **opts).each do |mb, tips|
      next if mb==:disjoint
      with_dir do
        l=%x/git -c color.ui=always log -n1 --date=short --format="%C(auto,green)%cd %C(auto)%h" #{mb}/
        date, short_hash=l.split
        nr=tips.map do |tip|
          `git name-rev --name-only --refs=#{tip.shellescape} #{mb}`.chomp
        end
        puts "#{date}: #{short_hash} – #{nr.join(', ')}"
      end
    end
  end
end

#output_commit_children(*commits) ⇒ Object



236
237
238
239
240
# File 'lib/git_helpers/extra_helpers.rb', line 236

def output_commit_children(*commits)
  commit_children(*commits).each do |commit, children|
    puts "#{commit}: #{children.join(", ")}"
  end
end

#output_commits_by_files(*files) ⇒ Object



273
274
275
276
277
# File 'lib/git_helpers/extra_helpers.rb', line 273

def output_commits_by_files(*files)
  commits_by_files(*files).each do |file, data|
    puts "- #{file}: #{data[:commits]} (active: #{data[:active]} days)"
  end
end

#output_log_commits_by_files(logopts = nil) ⇒ Object



255
256
257
258
259
# File 'lib/git_helpers/extra_helpers.rb', line 255

def output_log_commits_by_files(logopts=nil)
  log_commits_by_files(logopts).sort {|f1, f2| -f1[1] <=> -f2[1]}.each do |file, count|
    puts "- #{file}: #{count}"
  end
end

#output_removed_files(logopts = nil) ⇒ Object



211
212
213
214
215
216
# File 'lib/git_helpers/extra_helpers.rb', line 211

def output_removed_files(logopts=nil)
  r=removed_files(logopts)
  r.each do |file, data|
    puts "#{data[:date]} #{data[:commit]}^:#{file}"
  end
end

#output_trails(*args, **opts) ⇒ Object

only output trails present in the log options passed



324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
# File 'lib/git_helpers/extra_helpers.rb', line 324

def output_trails(*args, **opts)
  with_dir do
    commit=`git rev-parse --revs-only --default HEAD #{args.shelljoin}`.chomp
    merges=trails(commit, **opts)
    %x/git -c color.ui=always log --date=short --format="%C(auto,green)%cd %C(auto)%h%C(reset) %H" #{args.shelljoin}/.each_line do |l|
      date, short_hash, hash=l.split
      if merges.key?(hash)
        nr=merges[hash].map do |tip|
          `git name-rev --name-only --refs=#{tip.shellescape} #{hash}`.chomp
        end
        puts "#{date}: #{short_hash} – #{nr.join(', ')}"
      end
    end
  end
end

#removed_files(logopts = nil) ⇒ Object



193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
# File 'lib/git_helpers/extra_helpers.rb', line 193

def removed_files(logopts=nil)
  removed={}
  with_dir do
    commit=nil; date=nil
    %x/git log #{DefaultLogOptions} --raw --date=short --format="%h %cd" #{logopts}/.each_line do |l|
      l.chomp!
      case l
      when /^[0-9a-f]/
        commit, date=l.split(' ',2)
      when /^:/
        _old_mode, _new_mode, _old_hash, _new_hash, state, filename=l.split(' ',6)
        #keep earliest removal
        removed[filename]||={date: date, commit: commit} if state=="D"
      end
    end
  end
  removed
end

#trails(commit, remotes: true, tags: true) ⇒ Object

inspired by git-trail from https://github.com/cypher/dotfiles merges: key=branch point hash, values=tips names



291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
# File 'lib/git_helpers/extra_helpers.rb', line 291

def trails(commit, remotes: true, tags: true)
  merges={}
  with_dir do
    %x/git for-each-ref/.each_line do |l|
      hash, type, name=l.split
      next if type=="tags" and !tags
      next if type=="commit" && !name.start_with?("refs/heads/") and !remotes
      mb=`git merge-base #{commit.shellescape} #{hash}`.chomp
      mb=:disjoint if mb.empty?
      merges[mb]||=[]
      merges[mb] << name
    end
  end
  merges
end