gistory 0.1.6 → 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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 72836cca18fd26cede97fde21b76c9ae225356751cec131e9631e8c746241a26
4
- data.tar.gz: a62e021cc1fbf194f00e84722a89c7a05bc7eb152edf4c15f1d70531a1e986e4
3
+ metadata.gz: '013096cf87f86116fb9e56c4649dbfca9fddef5d0ee7b852d716863c878fe85c'
4
+ data.tar.gz: 99a1fdcfe15237525f30b4fc21b2228b41d7a21d72b14a6720ea4f1f896352c9
5
5
  SHA512:
6
- metadata.gz: b95cb0e28c162937b8533768d719050ae756117d2def8ba552b906636e00e282f983a1bae36860ce4afc2a7f5b3a9cbaea91873b71ce5fb24b9cf43f1f2a0707
7
- data.tar.gz: d3f43852128ca25fa2619084b3916f54cda3ba30999a208b025329c57f7dce48d04f3ac5247056ff8a0c61abc369d80dafd5af932a0e3f8410982c6d33b2ce7d
6
+ metadata.gz: 20a9c87950c34a0da71cad949bd46b5f3324ad7e0fccd3d7effa1189130ddaa9abdb04f3afdf6b16c796cf993039795666b1f57330c131fc01bf35b11ed0605a
7
+ data.tar.gz: 7980c0628a183fb59b9e3a32d40019a74faea1ba9069a071a3ed2bda994205139314d8d633f17d444a62ae0966b588e5fffc7d0f65919620bc6c055cfa589228
@@ -13,4 +13,4 @@ ratings:
13
13
  paths:
14
14
  - "**.rb"
15
15
  exclude_paths:
16
- - test/
16
+ - spec/
data/.gitignore CHANGED
@@ -8,4 +8,7 @@
8
8
  /spec/reports/
9
9
  /tmp/
10
10
 
11
+ # rspec failure tracking
12
+ .rspec_status
13
+
11
14
  NOTES.txt
data/.rspec ADDED
@@ -0,0 +1,3 @@
1
+ --format documentation
2
+ --color
3
+ --require spec_helper
@@ -1,26 +1,29 @@
1
- Documentation:
2
- Enabled: false
1
+ require: rubocop-rspec
2
+
3
+ AllCops:
4
+ TargetRubyVersion: 2.4
5
+ NewCops: enable
3
6
 
4
7
  Metrics/AbcSize:
5
- # The ABC size is a calculated magnitude, so this number can be a Fixnum or a Float.
6
- # http://c2.com/cgi/wiki?AbcMetric
7
8
  Max: 25
8
9
  Exclude:
9
- - 'test/**/*_test.rb' # ignore tests which typically have high B count due to many asserts
10
+ - 'spec/**/*_spec.rb'
10
11
 
11
- Metrics/ClassLength:
12
+ Metrics/BlockLength:
12
13
  Exclude:
13
- - 'test/**/*_test.rb'
14
+ - 'spec/**/*_spec.rb'
14
15
 
15
16
  Metrics/MethodLength:
16
17
  Max: 20
17
- Exclude:
18
- - 'test/**/*_test.rb'
19
18
 
20
- Metrics/LineLength:
19
+ Layout/LineLength:
21
20
  Max: 120
22
21
 
23
- Layout/EmptyLineAfterGuardClause:
22
+ Style/BlockDelimiters:
23
+ Exclude:
24
+ - 'spec/**/*_spec.rb'
25
+
26
+ Style/Documentation:
24
27
  Enabled: false
25
28
 
26
29
  Style/IfUnlessModifier:
@@ -28,3 +31,14 @@ Style/IfUnlessModifier:
28
31
 
29
32
  Style/FrozenStringLiteralComment:
30
33
  EnforcedStyle: always
34
+
35
+ Style/StringLiterals:
36
+ EnforcedStyle: double_quotes
37
+
38
+ # rubocop-rspec
39
+
40
+ RSpec/MultipleExpectations:
41
+ Max: 15
42
+
43
+ RSpec/ExampleLength:
44
+ Max: 15
@@ -1,7 +1,9 @@
1
1
  sudo: false
2
2
  language: ruby
3
+ script:
4
+ - bundle exec rspec
3
5
  rvm:
4
- - 2.4.0
5
- - 2.3.3
6
- - 2.2.6
6
+ - 2.6.6
7
+ - 2.5.8
8
+ - 2.4.10
7
9
  before_install: gem install bundler -v 1.17.3
data/Gemfile CHANGED
@@ -1,20 +1,13 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- source 'https://rubygems.org'
3
+ source "https://rubygems.org"
4
4
 
5
5
  gemspec
6
6
 
7
- group :development, :test do
8
- gem 'byebug' # debugger
9
- gem 'pry' # better console
10
- gem 'pry-byebug' # pry integration for byebug
11
- end
12
-
13
7
  group :test do
14
- gem 'coveralls', require: false
15
- gem 'flexmock' # mock library
16
- gem 'simplecov', require: false # code coverage
8
+ gem "coveralls", require: false
9
+ gem "simplecov", require: false # code coverage
17
10
  end
18
11
 
19
- local_gemfile = 'Gemfile.local'
12
+ local_gemfile = "Gemfile.local"
20
13
  eval_gemfile(local_gemfile) if File.exist?(local_gemfile)
data/README.md CHANGED
@@ -5,7 +5,7 @@
5
5
  [![Build Status](https://travis-ci.org/serch/gistory.svg?branch=master)](https://travis-ci.org/serch/gistory)
6
6
  [![Coverage Status](https://coveralls.io/repos/github/serch/gistory/badge.svg?branch=master)](https://coveralls.io/github/serch/gistory?branch=master)
7
7
 
8
- If you use bundler and git, and want to know when a gem you are using was updated, `gistory` comes to your rescue, simply:
8
+ If you use bundler and git and you want to know when a gem was updated, `gistory` comes to the rescue, simply:
9
9
 
10
10
  ```shell
11
11
  gem install gistory
@@ -14,6 +14,7 @@ gistory sidekiq
14
14
  ```
15
15
 
16
16
  and you'll see something like:
17
+
17
18
  ```
18
19
  Gem: sidekiq
19
20
  Current version: 4.2.7
@@ -25,11 +26,17 @@ Change history:
25
26
  4.1.4 on Wed, 9 Nov 2016 14:31 +01:00 (commit 05a3c549)
26
27
  ```
27
28
 
28
- By default `gistory` only looks at the last 100 changes to Gemfile.lock
29
- if you want to see farther in the past run:
29
+ By default `gistory` only looks at the last 100 commits made to the current branch.
30
+ If you want to see farther back in the past run:
31
+
32
+ ```shell
33
+ gistory sidekiq -m1000
34
+ ```
35
+
36
+ If you want to look at all changes to Gemfile.lock in all branches, use the `-a` switch:
30
37
 
31
38
  ```shell
32
- gistory sidekiq -m10000
39
+ gistory sidekiq -a
33
40
  ```
34
41
 
35
42
  Note that if the gem was added, then removed, and then added again, `gistory` will
@@ -44,4 +51,4 @@ only show the latest version changes up until it was removed.
44
51
  - remove bundler dep
45
52
  - add yard doc
46
53
  - do not print the warning text if there were no more changes in the lock file
47
- - find version with the longest length and pad all others to match it (f.i. rails has 4.2.8 and 4.2.7.1)
54
+ - link the commit SHA to the repo's hosting service, if any
data/Rakefile CHANGED
@@ -1,12 +1,8 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'bundler/gem_tasks'
4
- require 'rake/testtask'
3
+ require "bundler/gem_tasks"
4
+ require "rspec/core/rake_task"
5
5
 
6
- Rake::TestTask.new(:test) do |t|
7
- t.libs << 'test'
8
- t.libs << 'lib'
9
- t.test_files = FileList['test/**/*_test.rb']
10
- end
6
+ RSpec::Core::RakeTask.new(:spec)
11
7
 
12
- task default: :test
8
+ task default: :spec
@@ -1,14 +1,14 @@
1
1
  #!/usr/bin/env ruby
2
2
  # frozen_string_literal: true
3
3
 
4
- require 'bundler/setup'
5
- require 'gistory'
6
- require 'pry'
4
+ require "bundler/setup"
5
+ require "gistory"
6
+ require "pry"
7
7
 
8
8
  root_path = "#{File.dirname(__FILE__)}/.."
9
9
 
10
10
  # require all files in lib for quick access to them in the console
11
- Dir["#{root_path}/lib/**/*.rb"].each { |file| require file }
11
+ Dir["#{root_path}/lib/**/*.rb"].sort.each { |file| require file }
12
12
 
13
13
  def reload!
14
14
  verbosity = $VERBOSE
@@ -1,9 +1,9 @@
1
1
  #!/usr/bin/env ruby
2
2
  # frozen_string_literal: true
3
3
 
4
- lib = File.expand_path('../lib', __dir__)
4
+ lib = File.expand_path("../lib", __dir__)
5
5
  $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
6
6
 
7
- require 'gistory'
7
+ require "gistory"
8
8
 
9
9
  Gistory::Cli::Main.new(repo_path: Dir.getwd, args: ARGV).run
@@ -1,32 +1,36 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- lib = File.expand_path('lib', __dir__)
3
+ lib = File.expand_path("lib", __dir__)
4
4
  $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
5
- require 'gistory/version'
5
+ require "gistory/version"
6
6
 
7
7
  Gem::Specification.new do |spec|
8
- spec.name = 'gistory'
8
+ spec.name = "gistory"
9
9
  spec.version = Gistory::VERSION
10
10
  spec.platform = Gem::Platform::RUBY
11
- spec.required_ruby_version = '>= 2.2'
12
- spec.authors = ['Sergio Medina']
13
- spec.email = ['medinasergio@gmail.com']
11
+ spec.required_ruby_version = ">= 2.4"
12
+ spec.authors = ["Sergio Medina"]
13
+ spec.email = ["medinasergio@gmail.com"]
14
14
 
15
- spec.summary = 'Gistory: Know exactly when a gem was updated in your Gemfile.lock'
16
- spec.description = 'Gistory: Know exactly when a gem was updated in your Gemfile.lock'
17
- spec.homepage = 'https://www.github.com/serch/gistory'
18
- spec.licenses = ['MIT']
15
+ spec.summary = "Gistory: Know exactly when a gem was updated in your Gemfile.lock"
16
+ spec.description = "Gistory: Know exactly when a gem was updated in your Gemfile.lock"
17
+ spec.homepage = "https://www.github.com/serch/gistory"
18
+ spec.licenses = ["MIT"]
19
19
 
20
20
  spec.files = `git ls-files -z`.split("\x0").reject do |f|
21
21
  f.match(%r{^(test|spec|features)/})
22
22
  end
23
- spec.bindir = 'exe'
23
+ spec.bindir = "exe"
24
24
  spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
25
- spec.require_paths = ['lib']
25
+ spec.require_paths = ["lib"]
26
26
 
27
- spec.add_dependency 'bundler', '~> 1.0'
28
- spec.add_dependency 'colorize'
27
+ spec.add_dependency "bundler", "~> 1.0"
28
+ spec.add_dependency "colorize"
29
29
 
30
- spec.add_development_dependency 'minitest', '~> 5.0'
31
- spec.add_development_dependency 'rake', '~> 10.0'
30
+ spec.add_development_dependency "pry", "~> 0.13.1"
31
+ spec.add_development_dependency "pry-byebug", "~> 3.9.0"
32
+ spec.add_development_dependency "rake", "~> 13.0"
33
+ spec.add_development_dependency "rspec", "~> 3.9"
34
+ spec.add_development_dependency "rubocop"
35
+ spec.add_development_dependency "rubocop-rspec"
32
36
  end
@@ -1,17 +1,18 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'gistory/version'
3
+ require "gistory/version"
4
4
 
5
- require 'gistory/cli/main'
6
- require 'gistory/cli/arg_parser'
7
- require 'gistory/cli/io'
8
- require 'gistory/configuration'
5
+ require "gistory/cli/main"
6
+ require "gistory/cli/arg_parser"
7
+ require "gistory/cli/io"
8
+ require "gistory/configuration"
9
9
 
10
- require 'gistory/errors'
11
- require 'gistory/commit'
12
- require 'gistory/version_change'
13
- require 'gistory/git_repo'
14
- require 'gistory/change_log'
10
+ require "gistory/errors"
11
+ require "gistory/commit"
12
+ require "gistory/version_change"
13
+ require "gistory/git_repo"
14
+ require "gistory/lockfile_parser"
15
+ require "gistory/change_log"
15
16
 
16
17
  module Gistory
17
18
  class << self
@@ -1,10 +1,8 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'bundler'
4
-
5
3
  module Gistory
6
4
  class ChangeLog
7
- LOCKFILE = 'Gemfile.lock'.freeze
5
+ LOCKFILE = "Gemfile.lock"
8
6
 
9
7
  def initialize(repo:)
10
8
  @repo = repo
@@ -12,43 +10,41 @@ module Gistory
12
10
 
13
11
  def changelog_for_gem(gem_name)
14
12
  version_changes = []
15
- lockfile_changes = @repo.changes_to_file(LOCKFILE)
13
+ commits_with_changes = @repo.changes_to_file(LOCKFILE)
16
14
 
17
15
  # no lockfile found or no changes to the lockfile found
18
- return [] if lockfile_changes.empty?
16
+ return [] if commits_with_changes.empty?
19
17
 
20
- previous_commit = lockfile_changes.shift
21
- previous_gem_spec = gem_spec_at_commit_hash(previous_commit.short_hash, gem_name)
18
+ previous_commit = commits_with_changes.shift
19
+ previous_gem_spec = gem_version_at_commit_hash(previous_commit.short_hash, gem_name)
22
20
  # only one change to the lockfile was found and the gem was not there
23
21
  return [] if previous_gem_spec.nil?
24
22
 
25
- lockfile_changes.each do |current_commit|
26
- current_gem_spec = gem_spec_at_commit_hash(current_commit.short_hash, gem_name)
23
+ commits_with_changes.each do |current_commit|
24
+ current_gem_spec = gem_version_at_commit_hash(current_commit.short_hash, gem_name)
27
25
 
28
26
  # we reached the end, the gem didn't exist back then
29
27
  # TODO: what if it was added then removed and then added again?
30
28
  break if current_gem_spec.nil?
31
29
 
32
- if current_gem_spec.version.to_s != previous_gem_spec.version.to_s
33
- version_changes << VersionChange.new(commit: previous_commit, version: previous_gem_spec.version)
30
+ if current_gem_spec != previous_gem_spec
31
+ version_changes << VersionChange.new(commit: previous_commit, version: previous_gem_spec)
34
32
  end
35
33
 
36
34
  previous_gem_spec = current_gem_spec
37
35
  previous_commit = current_commit
38
36
  end
39
37
 
40
- version_changes << VersionChange.new(commit: previous_commit, version: previous_gem_spec.version)
38
+ version_changes << VersionChange.new(commit: previous_commit, version: previous_gem_spec)
41
39
 
42
40
  version_changes
43
41
  end
44
42
 
45
43
  private
46
44
 
47
- def gem_spec_at_commit_hash(commit_hash, gem_name)
45
+ def gem_version_at_commit_hash(commit_hash, gem_name)
48
46
  lockfile_content = @repo.file_content_at_commit(commit_hash, LOCKFILE)
49
- lockfile = Bundler::LockfileParser.new(lockfile_content)
50
- gem_spec = lockfile.specs.find { |spec| spec.name == gem_name }
51
- gem_spec
47
+ LockfileParser.new(lockfile_content: lockfile_content).gem_version(gem_name)
52
48
  end
53
49
  end
54
50
  end
@@ -1,6 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'optparse'
3
+ require "optparse"
4
4
 
5
5
  module Gistory
6
6
  module Cli
@@ -18,8 +18,8 @@ module Gistory
18
18
  parse_gem_name
19
19
  @io.error("extra parameters ignored: #{@args}") unless @args.count.zero?
20
20
  @config
21
- rescue OptionParser::InvalidOption => err
22
- raise(Gistory::ParserError, err.message)
21
+ rescue OptionParser::InvalidOption => e
22
+ raise(Gistory::ParserError, e.message)
23
23
  end
24
24
 
25
25
  def to_s
@@ -30,53 +30,67 @@ module Gistory
30
30
 
31
31
  def parse_gem_name
32
32
  gem_name = @args.shift
33
- raise(Gistory::ParserError, 'No gem specified') unless gem_name
33
+ raise(Gistory::ParserError, "No gem specified") unless gem_name
34
+
34
35
  @config.gem_name = gem_name
35
36
  end
36
37
 
37
38
  def create_parser(config)
38
39
  parser = OptionParser.new
39
- parser.banner = 'Usage: gistory <gem_name> [options]'
40
+ parser.banner = "Usage: gistory <gem_name> [options]"
40
41
 
41
- add_specific_options(parser, config)
42
- add_common_options(parser)
42
+ add_options(parser, config)
43
43
 
44
44
  parser
45
45
  end
46
46
 
47
- def add_specific_options(parser, config)
48
- parser.separator ''
49
- parser.separator 'Specific options:'
47
+ def add_options(parser, config)
48
+ parser.separator ""
49
+ parser.separator "Options:"
50
50
 
51
- add_max_lockfile_changes(parser, config)
51
+ add_max_fetched_commits(parser, config)
52
+ add_use_commits_from_all_branches(parser, config)
53
+ add_output_commit_hashes_only(parser, config)
54
+ add_help(parser)
55
+ add_version(parser)
52
56
  end
53
57
 
54
- def add_common_options(parser)
55
- parser.separator ''
56
- parser.separator 'Common options:'
58
+ def add_max_fetched_commits(parser, config)
59
+ default = config.max_fetched_commits
60
+ description = "max number of commits to be fetched (default #{default})"
61
+ parser.on("-m", "--max-fetched-commits [Integer]", Integer, description) do |m|
62
+ raise(Gistory::ParserError, "argument --max-fetched-commits must be an integer") if m.nil?
57
63
 
58
- add_help(parser)
59
- add_version(parser)
64
+ config.max_fetched_commits = m
65
+ end
66
+ end
67
+
68
+ def add_use_commits_from_all_branches(parser, config)
69
+ description = "use commits from all branches " \
70
+ "(by default it uses only commits made to the current branch)"
71
+ parser.on("-a", "--all-branches", description) do |a|
72
+ config.all_branches = a
73
+ end
60
74
  end
61
75
 
62
- def add_max_lockfile_changes(parser, config)
63
- default = config.max_lockfile_changes
64
- description = "max number of changes to the lock file (default #{default})"
65
- parser.on('-m', '--max-lockfile-changes [INTEGER]', Integer, description) do |m|
66
- raise(Gistory::ParserError, 'argument --max-lockfile-changes must be an integer') if m.nil?
67
- config.max_lockfile_changes = m
76
+ def add_output_commit_hashes_only(parser, config)
77
+ option_switch = "--hashes-only"
78
+ parser.on(option_switch,
79
+ "output commit hashes only so they can be piped",
80
+ "for example: gistory #{option_switch} sidekiq | xargs git show") do |ho|
81
+ config.output_commit_hashes_only = ho
68
82
  end
69
83
  end
70
84
 
71
85
  def add_help(parser)
72
- parser.on_tail('-h', '--help', 'Show this message') do
86
+ parser.on_tail("-h", "--help", "Show this message") do
73
87
  @io.puts parser
74
88
  exit
75
89
  end
76
90
  end
77
91
 
78
92
  def add_version(parser)
79
- parser.on_tail('--version', 'Show version') do
93
+ parser.on_tail("--version", "Show version") do
80
94
  @io.puts "gistory version #{Gistory::VERSION}"
81
95
  exit
82
96
  end
@@ -1,6 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'colorize'
3
+ require "colorize"
4
4
 
5
5
  module Gistory
6
6
  module Cli
@@ -14,11 +14,11 @@ module Gistory
14
14
  parser = Cli::ArgParser.new(args: @args, io: @io)
15
15
  config = parser.parse
16
16
  history(repo, config.gem_name)
17
- rescue Gistory::ParserError => error
18
- @io.error error.message
17
+ rescue Gistory::ParserError => e
18
+ @io.error e.message
19
19
  @io.puts parser
20
- rescue Gistory::Error => error
21
- @io.error error.message
20
+ rescue Gistory::Error => e
21
+ @io.error e.message
22
22
  end
23
23
 
24
24
  private
@@ -30,18 +30,48 @@ module Gistory
30
30
  raise(Gistory::Error, "Gem '#{gem_name}' not found in lock file, maybe a typo?")
31
31
  end
32
32
 
33
+ if Gistory.config.output_commit_hashes_only?
34
+ print_commit_hashes_only(changes)
35
+ else
36
+ print_full_output(gem_name, changes)
37
+ end
38
+ end
39
+
40
+ def print_commit_hashes_only(changes)
41
+ changes.each { |change| @io.puts change.short_hash }
42
+ end
43
+
44
+ def print_full_output(gem_name, changes)
33
45
  @io.puts "Gem: #{gem_name}"
34
46
  @io.puts "Current version: #{changes.first.version}"
35
- @io.puts ''
47
+ @io.puts ""
48
+
49
+ print_change_history(changes)
50
+
51
+ @io.puts ""
52
+
53
+ print_configuration_info
54
+ end
55
+
56
+ def print_change_history(changes)
57
+ @io.puts "Change history:"
58
+ max_length = changes.map { |c| c.version.length }.max
36
59
 
37
- @io.puts 'Change history:'
38
60
  changes.each do |change|
39
- @io.puts "#{change.version} on #{change.date.strftime('%a, %e %b %Y %H:%M %Z')} (commit #{change.short_hash})"
61
+ @io.puts "#{change.version.ljust(max_length)} on #{change.date.strftime('%a, %e %b %Y %H:%M %Z')} " \
62
+ "(commit #{change.short_hash})"
63
+ end
64
+ end
65
+
66
+ def print_configuration_info
67
+ max = Gistory.config.max_fetched_commits
68
+ if Gistory.config.all_branches?
69
+ @io.puts "The last #{max} changes to the lock file were fetched."
70
+ else
71
+ @io.puts "The last #{max} commits made to the current branch were fetched."
40
72
  end
41
73
 
42
- @io.puts ''
43
- max = Gistory.config.max_lockfile_changes
44
- @io.puts "The last #{max} changes to the lock file were taken into account, to see farther in the past use the -m switch" # rubocop:disable Metrics/LineLength
74
+ @io.puts "To see farther in the past use the -m switch"
45
75
  end
46
76
  end
47
77
  end
@@ -1,6 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'date'
3
+ require "date"
4
4
 
5
5
  module Gistory
6
6
  class Commit
@@ -11,5 +11,9 @@ module Gistory
11
11
  @date = DateTime.parse(date.to_s)
12
12
  freeze
13
13
  end
14
+
15
+ def to_s
16
+ "Commit #{short_hash} on #{date}"
17
+ end
14
18
  end
15
19
  end
@@ -2,10 +2,21 @@
2
2
 
3
3
  module Gistory
4
4
  class Configuration
5
- attr_accessor :gem_name, :max_lockfile_changes
5
+ attr_accessor :gem_name, :max_fetched_commits
6
+ attr_writer :all_branches, :output_commit_hashes_only
6
7
 
7
8
  def initialize
8
- @max_lockfile_changes = 100
9
+ @max_fetched_commits = 100
10
+ @all_branches = false
11
+ @output_commit_hashes_only = false
12
+ end
13
+
14
+ def all_branches?
15
+ @all_branches
16
+ end
17
+
18
+ def output_commit_hashes_only?
19
+ @output_commit_hashes_only
9
20
  end
10
21
  end
11
22
  end
@@ -1,17 +1,18 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'English'
3
+ require "English"
4
4
 
5
5
  module Gistory
6
6
  class GitRepo
7
7
  def initialize(path:)
8
- raise(Gistory::Error, 'This is not a valid git repository') unless Dir.exist?(File.join(path, '.git'))
9
- raise(Gistory::Error, 'git is not available, please install it') unless git_cli_available?
8
+ raise(Gistory::Error, "This is not a valid git repository") unless Dir.exist?(File.join(path, ".git"))
9
+ raise(Gistory::Error, "git is not available, please install it") unless git_cli_available?
10
10
  end
11
11
 
12
12
  def changes_to_file(filename)
13
- max_count = Gistory.config.max_lockfile_changes
14
- hashes_and_dates = git("log --pretty=format:'%h|%cD' --max-count=#{max_count} --follow #{filename}")
13
+ max_count = Gistory.config.max_fetched_commits
14
+ strategy = git_log_strategy(filename)
15
+ hashes_and_dates = git("log --pretty=format:'%h|%cD' --max-count=#{max_count} #{strategy}")
15
16
  to_commits(hashes_and_dates.split("\n"))
16
17
  end
17
18
 
@@ -21,20 +22,30 @@ module Gistory
21
22
 
22
23
  private
23
24
 
25
+ def git_log_strategy(filename)
26
+ if Gistory.config.all_branches?
27
+ "--follow #{filename}"
28
+ else
29
+ # TODO: filter out commits that did not introduce changes to the lock file
30
+ "--first-parent"
31
+ end
32
+ end
33
+
24
34
  def git_cli_available?
25
- system('which git > /dev/null 2>&1')
35
+ system("which git > /dev/null 2>&1")
26
36
  end
27
37
 
28
38
  def to_commits(hashes_and_dates)
29
39
  hashes_and_dates.map do |hash_and_date|
30
- commit_hash, date = hash_and_date.split('|')
40
+ commit_hash, date = hash_and_date.split("|")
31
41
  Commit.new(short_hash: commit_hash, date: date)
32
42
  end
33
43
  end
34
44
 
35
45
  def git(command)
36
46
  out = `git #{command}`
37
- raise 'Git CLI command failed' unless $CHILD_STATUS.success?
47
+ raise "Git CLI command failed" unless $CHILD_STATUS.success?
48
+
38
49
  out
39
50
  end
40
51
  end
@@ -0,0 +1,26 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "bundler"
4
+
5
+ module Gistory
6
+ class LockfileParser
7
+ def initialize(lockfile_content:)
8
+ @lockfile_content = lockfile_content
9
+ end
10
+
11
+ def gem_version(gem_name)
12
+ lockfile = Bundler::LockfileParser.new(@lockfile_content)
13
+ gem_spec = lockfile.specs.find { |spec| spec.name == gem_name }
14
+ gem_spec ? gem_spec.version.to_s : nil
15
+ rescue Bundler::LockfileError => _e
16
+ # bundler could not parse the lockfile
17
+ # f.i. it could have been committed with merge conflicts
18
+ # try to parse it with a regex
19
+ # gem version looks like " byebug (9.0.6)"
20
+ # TODO: what if the gem was in the merge conflict?
21
+ regexp = /\n\s{4}#{gem_name} \((?<version>.+)\)\n/
22
+ matches = @lockfile_content.match(regexp)
23
+ matches ? matches[:version] : nil
24
+ end
25
+ end
26
+ end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Gistory
4
- VERSION = '0.1.6'.freeze
4
+ VERSION = "0.3.0"
5
5
  end
@@ -1,6 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'forwardable'
3
+ require "forwardable"
4
4
 
5
5
  module Gistory
6
6
  class VersionChange
@@ -14,5 +14,9 @@ module Gistory
14
14
  @version = version
15
15
  freeze
16
16
  end
17
+
18
+ def to_s
19
+ "Version #{version} (on #{date} by #{short_hash})"
20
+ end
17
21
  end
18
22
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: gistory
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.6
4
+ version: 0.3.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Sergio Medina
8
- autorequire:
8
+ autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2019-01-29 00:00:00.000000000 Z
11
+ date: 2020-09-12 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -39,33 +39,89 @@ dependencies:
39
39
  - !ruby/object:Gem::Version
40
40
  version: '0'
41
41
  - !ruby/object:Gem::Dependency
42
- name: minitest
42
+ name: pry
43
43
  requirement: !ruby/object:Gem::Requirement
44
44
  requirements:
45
45
  - - "~>"
46
46
  - !ruby/object:Gem::Version
47
- version: '5.0'
47
+ version: 0.13.1
48
48
  type: :development
49
49
  prerelease: false
50
50
  version_requirements: !ruby/object:Gem::Requirement
51
51
  requirements:
52
52
  - - "~>"
53
53
  - !ruby/object:Gem::Version
54
- version: '5.0'
54
+ version: 0.13.1
55
+ - !ruby/object:Gem::Dependency
56
+ name: pry-byebug
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - "~>"
60
+ - !ruby/object:Gem::Version
61
+ version: 3.9.0
62
+ type: :development
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - "~>"
67
+ - !ruby/object:Gem::Version
68
+ version: 3.9.0
55
69
  - !ruby/object:Gem::Dependency
56
70
  name: rake
57
71
  requirement: !ruby/object:Gem::Requirement
58
72
  requirements:
59
73
  - - "~>"
60
74
  - !ruby/object:Gem::Version
61
- version: '10.0'
75
+ version: '13.0'
76
+ type: :development
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - "~>"
81
+ - !ruby/object:Gem::Version
82
+ version: '13.0'
83
+ - !ruby/object:Gem::Dependency
84
+ name: rspec
85
+ requirement: !ruby/object:Gem::Requirement
86
+ requirements:
87
+ - - "~>"
88
+ - !ruby/object:Gem::Version
89
+ version: '3.9'
62
90
  type: :development
63
91
  prerelease: false
64
92
  version_requirements: !ruby/object:Gem::Requirement
65
93
  requirements:
66
94
  - - "~>"
67
95
  - !ruby/object:Gem::Version
68
- version: '10.0'
96
+ version: '3.9'
97
+ - !ruby/object:Gem::Dependency
98
+ name: rubocop
99
+ requirement: !ruby/object:Gem::Requirement
100
+ requirements:
101
+ - - ">="
102
+ - !ruby/object:Gem::Version
103
+ version: '0'
104
+ type: :development
105
+ prerelease: false
106
+ version_requirements: !ruby/object:Gem::Requirement
107
+ requirements:
108
+ - - ">="
109
+ - !ruby/object:Gem::Version
110
+ version: '0'
111
+ - !ruby/object:Gem::Dependency
112
+ name: rubocop-rspec
113
+ requirement: !ruby/object:Gem::Requirement
114
+ requirements:
115
+ - - ">="
116
+ - !ruby/object:Gem::Version
117
+ version: '0'
118
+ type: :development
119
+ prerelease: false
120
+ version_requirements: !ruby/object:Gem::Requirement
121
+ requirements:
122
+ - - ">="
123
+ - !ruby/object:Gem::Version
124
+ version: '0'
69
125
  description: 'Gistory: Know exactly when a gem was updated in your Gemfile.lock'
70
126
  email:
71
127
  - medinasergio@gmail.com
@@ -77,6 +133,7 @@ files:
77
133
  - ".codeclimate.yml"
78
134
  - ".coveralls.yml"
79
135
  - ".gitignore"
136
+ - ".rspec"
80
137
  - ".rubocop.yml"
81
138
  - ".travis.yml"
82
139
  - Gemfile
@@ -96,13 +153,14 @@ files:
96
153
  - lib/gistory/configuration.rb
97
154
  - lib/gistory/errors.rb
98
155
  - lib/gistory/git_repo.rb
156
+ - lib/gistory/lockfile_parser.rb
99
157
  - lib/gistory/version.rb
100
158
  - lib/gistory/version_change.rb
101
159
  homepage: https://www.github.com/serch/gistory
102
160
  licenses:
103
161
  - MIT
104
162
  metadata: {}
105
- post_install_message:
163
+ post_install_message:
106
164
  rdoc_options: []
107
165
  require_paths:
108
166
  - lib
@@ -110,16 +168,15 @@ required_ruby_version: !ruby/object:Gem::Requirement
110
168
  requirements:
111
169
  - - ">="
112
170
  - !ruby/object:Gem::Version
113
- version: '2.2'
171
+ version: '2.4'
114
172
  required_rubygems_version: !ruby/object:Gem::Requirement
115
173
  requirements:
116
174
  - - ">="
117
175
  - !ruby/object:Gem::Version
118
176
  version: '0'
119
177
  requirements: []
120
- rubyforge_project:
121
- rubygems_version: 2.7.8
122
- signing_key:
178
+ rubygems_version: 3.0.3
179
+ signing_key:
123
180
  specification_version: 4
124
181
  summary: 'Gistory: Know exactly when a gem was updated in your Gemfile.lock'
125
182
  test_files: []