git_miner 0.1.0 → 0.2.3

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: 0aa67e6c72b1527778f786fb604807437789516188c2b0aac1d6520701571762
4
- data.tar.gz: 9323e1fcd8d7ab220b10ef465baf8a158252b7bf6f317366707f7954a69f11e3
3
+ metadata.gz: 6a915c54b13e195ecbe3b95b74e4244702fd9bec71a984a87e59a02080ebddef
4
+ data.tar.gz: 4661c7660d691af5e236064a7da19460d5adbad3f44881b3268d955e2e59f0ea
5
5
  SHA512:
6
- metadata.gz: 6d6e3c36b03808d24f4e8ae8dafd7cec12da24d586cabc637d667ed76a5c9c446f017764a80f57a1cefd2e0ca349c61bc2eb3948cb76998c97992aaa4497218b
7
- data.tar.gz: aaeef8f54d352eb93649de28f2d54f107b1ac7e5d856505660f9a7a649aa8c436062216ffaf2ca5da04771e3cd35292b9963fa620fb91213bdcd804c904e8ca6
6
+ metadata.gz: 5ed7b15ee18e8662845858310b5eaab75ad9e719f43c5f190dbaaf465905ab7b66261f4cea721f706b54fb41a7768a0da55ddd8282c284b12dd6d3aeb32a5ded
7
+ data.tar.gz: 0a143498f08746fcb3fa71f69988209284ef65f7e5aec5aae2e1c952f599bcc25d93735102076d988b3ab4a8d5169e493c04a8738b42c04686a686a503557c10
data/.gitignore CHANGED
@@ -11,3 +11,4 @@
11
11
  .rspec_status
12
12
 
13
13
  *.gem
14
+ lib/*.bundle
data/Gemfile.lock CHANGED
@@ -1,17 +1,17 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- git_miner (0.1.0)
4
+ git_miner (0.2.2)
5
5
  concurrent-ruby (~> 1.1)
6
6
  parallel (~> 1.17)
7
7
 
8
8
  GEM
9
9
  remote: https://rubygems.org/
10
10
  specs:
11
- concurrent-ruby (1.1.5)
11
+ concurrent-ruby (1.1.9)
12
12
  diff-lcs (1.3)
13
- parallel (1.17.0)
14
- rake (10.5.0)
13
+ parallel (1.21.0)
14
+ rake (13.0.1)
15
15
  rake-compiler (1.0.7)
16
16
  rake
17
17
  rspec (3.8.0)
@@ -34,9 +34,9 @@ PLATFORMS
34
34
  DEPENDENCIES
35
35
  bundler (~> 2.0)
36
36
  git_miner!
37
- rake (~> 10.0)
37
+ rake (~> 13.0)
38
38
  rake-compiler (~> 1.0)
39
39
  rspec (~> 3.0)
40
40
 
41
41
  BUNDLED WITH
42
- 2.0.1
42
+ 2.2.32
data/README.md CHANGED
@@ -1,28 +1,53 @@
1
1
  # GitMiner
2
2
 
3
- Pet project I build experimenting with different concepts.
3
+ Pet project I built to experiment with different concepts.
4
4
 
5
- GitMiner allow for "mining" of vanity git prefixes.
5
+ GitMiner allow "mining" of vanity Git SHA1 prefixes.
6
6
 
7
- This gem is a work in progress (core functionality is working).
7
+ The HEAD commit is altered via variations over committer and author timestamp adjustments. Other commit metadata such as commit message or description are left as their original.
8
8
 
9
9
 
10
10
  ## Installation
11
11
 
12
- Installation will add the `git-mine` binary.
12
+ These options will add the `git-mine` binary which act as a Git custom command: `git mine`.
13
+
14
+ ### Rubygem
13
15
 
14
16
  ```ruby
15
17
  gem 'git_miner'
16
18
  ```
17
19
 
20
+ ### Manual
21
+
22
+ ```
23
+ gem build git_miner.gemspec
24
+ gem install --local git_miner-*.gem
25
+ ```
18
26
 
19
27
  ## Usage
20
28
 
21
- Though `git`, using `git mine [DESIRED_PREFIX]` will invoke the required logic.
29
+ `git mine [DESIRED_PREFIX]` will amend the current HEAD commit with a new mined SHA.
22
30
 
23
31
  Eg.:
24
32
  ```
25
33
  git mine c0ffee
26
34
  ```
27
35
 
28
- Some extra options are available. `git-mine -h` will display the help section (default options are optimised for performance).
36
+ Some extra options are available (experimental):
37
+ ```
38
+ $ git mine -h
39
+ Usage: git mine [options]
40
+ --engine [ruby|c] Set the engine (default: ruby)
41
+ --dispatch [simple|parallel] Set the dispatch (default: parallel)
42
+ --verbose Run verbosely (default: false)
43
+ --register [prefix] Register automated post commit git hook
44
+ -v, --version Returns the current version
45
+ -h, --help Show this message
46
+ ```
47
+
48
+
49
+ ### Development
50
+
51
+ ```
52
+ [path]/git_miner/bin/git-mine ...
53
+ ```
data/Rakefile CHANGED
@@ -7,7 +7,7 @@ RSpec::Core::RakeTask.new(:spec)
7
7
  task :default => :spec
8
8
 
9
9
  Rake::ExtensionTask.new "git_miner_ext" do |ext|
10
- ext.lib_dir = "lib/git_miner"
10
+ ext.lib_dir = "lib"
11
11
  end
12
12
 
13
- Rake::Task[:test].prerequisites << :compile
13
+ Rake::Task[:spec].prerequisites << :compile
data/bin/git-mine CHANGED
@@ -2,8 +2,7 @@
2
2
 
3
3
  STDOUT.sync = true
4
4
 
5
- require 'git_miner'
6
-
5
+ require File.join(__dir__, '..', 'lib', 'git_miner')
7
6
 
8
7
  require 'optparse'
9
8
 
@@ -12,28 +11,53 @@ options = {
12
11
  dispatch: :parallel,
13
12
  }
14
13
 
15
- OptionParser.new do |opts|
16
- opts.banner = "Usage: example.rb [options]"
14
+ parser = OptionParser.new do |opts|
15
+ opts.banner = "Usage: git mine [options]"
16
+
17
+ opts.on("--engine [ruby|c]", [:ruby, :c], "Set the engine (default: ruby)") do |engine|
18
+ options[:engine] = engine
19
+ end
20
+
21
+ opts.on("--dispatch [simple|parallel]", [:simple, :parallel], "Set the dispatch (default: parallel)") do |dispatch|
22
+ options[:dispatch] = dispatch
23
+ end
24
+
25
+ opts.on("--verbose", "Run verbosely (default: false)") do |verbose|
26
+ options[:verbose] = verbose
27
+ end
28
+
29
+ opts.on("--register [prefix]", "Register automated post commit git hook") do |prefix|
30
+ if prefix.nil?
31
+ puts parser
32
+ exit 1
33
+ end
17
34
 
18
- opts.on("--engine [ruby|c]", [:ruby, :c], "Desired engine (default: ruby)") do |x|
19
- options[:engine] = x
35
+ GitMiner::RegisterHook.register(prefix: prefix)
36
+ exit
20
37
  end
21
38
 
22
- opts.on("--dispatch [simple|parallel]", [:simple, :parallel], "Desired dispatch (default: parallel)") do |x|
23
- options[:dispatch] = x
39
+ opts.on_tail("-v", "--version", "Returns the current version") do
40
+ puts "GitMiner #{GitMiner::VERSION}"
41
+ exit
24
42
  end
25
43
 
26
44
  opts.on_tail("-h", "--help", "Show this message") do
27
45
  puts opts
28
46
  exit
29
47
  end
30
- end.parse!
48
+ end
49
+
50
+ parser.parse!
31
51
 
32
52
  unless ARGV.size == 1
33
- puts opts
53
+ puts parser
34
54
  exit 1
35
55
  end
36
56
 
57
+ GitMiner.logger.level = options[:verbose] ? Logger::DEBUG : Logger::INFO
58
+
59
+ GitMiner.logger.debug("OptionParser: #{options.inspect}")
60
+
37
61
  prefix = ARGV.first
38
62
 
39
63
  engine = case(options[:engine])
data/git_miner.gemspec CHANGED
@@ -33,13 +33,13 @@ Gem::Specification.new do |spec|
33
33
  spec.executables = ["git-mine"]
34
34
  spec.require_paths = ["lib"]
35
35
 
36
- spec.extensions = %w[ext/git_miner_ext/extconf.rb]
36
+ spec.extensions = Dir["ext/**/extconf.rb"]
37
37
 
38
38
  spec.add_runtime_dependency "parallel", "~> 1.17"
39
39
  spec.add_runtime_dependency "concurrent-ruby", "~> 1.1"
40
40
 
41
41
  spec.add_development_dependency "bundler", "~> 2.0"
42
- spec.add_development_dependency "rake", "~> 10.0"
42
+ spec.add_development_dependency "rake", "~> 13.0"
43
43
  spec.add_development_dependency "rspec", "~> 3.0"
44
44
  spec.add_development_dependency "rake-compiler", "~> 1.0"
45
45
  end
@@ -1,7 +1,11 @@
1
1
  module GitMiner
2
2
  class Core
3
3
  def initialize(engine:, dispatch:, prefix:)
4
- puts "Initializing with engine '#{engine}'. dispatch '#{dispatch}' and prefix '#{prefix}'"
4
+ GitMiner.logger.info("Initializing")
5
+
6
+ GitMiner.logger.debug("- Prefix: #{prefix}")
7
+ GitMiner.logger.debug("- Engine: #{engine::IDENTIFIER}")
8
+ GitMiner.logger.debug("- Dispatch: #{dispatch::IDENTIFIER}")
5
9
 
6
10
  @prefix = prefix
7
11
 
@@ -35,14 +39,14 @@ module GitMiner
35
39
  end
36
40
 
37
41
  unless @prefix[/^[0-9a-f]{1,32}$/]
38
- raise "Invalid prefix, expected '^[0-9a-f]{1,32}$'"
42
+ raise(UserError, "Invalid prefix, expected '^[0-9a-f]{1,32}$'")
39
43
  end
40
44
 
41
- puts "Validations: Successful"
45
+ GitMiner.logger.debug("Prefix validation: Accepted")
42
46
  end
43
47
 
44
48
  def mine
45
- puts "Mining for sha"
49
+ GitMiner.logger.info("Mining for SHA: #{@prefix}")
46
50
 
47
51
  @mining_result = @dispatch.execute
48
52
  end
@@ -50,10 +54,9 @@ module GitMiner
50
54
  def report
51
55
  raise "Prerequisite: Require mining to be completed first" unless @mining_result
52
56
 
53
- puts "Mining results:"
54
- puts "- New sha: #{@mining_result.sha}"
55
- puts "- Author offset: #{@mining_result.author_offset}"
56
- puts "- Committer offset: #{@mining_result.committer_offset}"
57
+ GitMiner.logger.debug("Mining completed.")
58
+ GitMiner.logger.debug("Author offset: #{@mining_result.author_offset}")
59
+ GitMiner.logger.debug("Committer offset: #{@mining_result.committer_offset}")
57
60
  end
58
61
 
59
62
  def alter
@@ -62,7 +65,10 @@ module GitMiner
62
65
  author_date = @now - @mining_result.author_offset
63
66
  committer_date = @now - @mining_result.committer_offset
64
67
 
68
+ GitMiner.logger.debug("Amending git")
65
69
  GitUtil.update_current_ref(author_date, committer_date)
70
+
71
+ GitMiner.logger.info("New SHA: #{@mining_result.sha}")
66
72
  end
67
73
  end
68
74
  end
@@ -1,6 +1,8 @@
1
1
  module GitMiner
2
2
  module Dispatch
3
3
  class AbstractDispatch
4
+ IDENTIFIER = "N/A"
5
+
4
6
  BATCH_SIZE = 50_000
5
7
 
6
8
  def initialize(prefix:, engine:)
@@ -4,6 +4,8 @@ require 'concurrent'
4
4
  module GitMiner
5
5
  module Dispatch
6
6
  class ParallelDispatch < AbstractDispatch
7
+ IDENTIFIER = "Parallel"
8
+
7
9
  class ShaFound < StandardError
8
10
  attr_reader :result
9
11
 
@@ -1,6 +1,8 @@
1
1
  module GitMiner
2
2
  module Dispatch
3
3
  class SimpleDispatch < AbstractDispatch
4
+ IDENTIFIER = "Simple"
5
+
4
6
  def perform
5
7
  loop do
6
8
  result = @engine.mine(
@@ -1,6 +1,7 @@
1
1
  module GitMiner
2
2
  module Engine
3
3
  class AbstractEngine
4
+ IDENTIFIER = "N/A"
4
5
 
5
6
  def sha1(_str)
6
7
  raise NotImplementedError
@@ -1,10 +1,14 @@
1
- require 'git_miner_ext'
1
+ require 'openssl'
2
+
3
+ require File.join(__dir__, '..', '..', 'git_miner_ext')
2
4
 
3
5
  module GitMiner
4
6
  module Engine
5
7
  class CExtensionEngine < AbstractEngine
6
8
  include GitMinerExt
7
9
 
10
+ IDENTIFIER = "CExtension"
11
+
8
12
  def sha1(str)
9
13
  c_sha1_hexdigest(str)
10
14
  end
@@ -3,6 +3,8 @@ require 'digest'
3
3
  module GitMiner
4
4
  module Engine
5
5
  class RubyEngine < AbstractEngine
6
+ IDENTIFIER = "Ruby"
7
+
6
8
  def sha1(str)
7
9
  Digest::SHA1.hexdigest(str)
8
10
  end
@@ -26,7 +28,7 @@ module GitMiner
26
28
  end
27
29
  end
28
30
 
29
- return
31
+ nil
30
32
  end
31
33
 
32
34
  private
@@ -34,9 +34,10 @@ module GitMiner
34
34
  private
35
35
 
36
36
  def shell(cmd, environment: {}, stdin_data: nil)
37
- puts "System call: #{cmd}"
38
- puts "environment: #{environment.inspect}" unless environment.empty?
39
- puts "stdin_data: #{stdin_data}" if stdin_data
37
+ GitMiner.logger.debug("System call")
38
+ GitMiner.logger.debug("- cmd: #{cmd}")
39
+ GitMiner.logger.debug("- environment: #{environment.inspect}") unless environment.empty?
40
+ GitMiner.logger.debug("- stdin: #{stdin_data}") if stdin_data
40
41
 
41
42
  output, status = Open3.capture2(environment, cmd, stdin_data: stdin_data) #, chdir: @working_directory
42
43
 
@@ -44,7 +45,7 @@ module GitMiner
44
45
  raise "Error on system call: #{output}, #{status}"
45
46
  end
46
47
 
47
- puts "result: #{output}"
48
+ GitMiner.logger.debug("- result => #{output.strip}")
48
49
 
49
50
  output
50
51
  end
@@ -28,22 +28,24 @@ module GitMiner
28
28
  end
29
29
 
30
30
  def report(count)
31
- info = []
32
-
33
31
  percentage = count * 100 / @combinations.to_f
34
- info << "#{percentage.round(2)}%"
32
+ info = []
35
33
 
36
34
  historic_count = @historic.last[:count] - @historic.first[:count]
37
35
  historic_delay = @historic.last[:timestamp] - @historic.first[:timestamp]
38
36
  if historic_delay > 0
39
37
  per_sec = historic_count / historic_delay
40
- info << "hash: #{per_sec.round(2)}/s"
38
+ info << "hash: #{'%.0f' % per_sec}/s"
41
39
 
42
40
  per_sec = (@historic.last[:batch] - @historic.first[:batch]) / historic_delay
43
- info << "batches: #{per_sec.round(2)}/s"
41
+ info << "batches: #{'%.2f' % per_sec}/s"
44
42
  end
45
43
 
46
- puts info.join(', ')
44
+ if info.empty?
45
+ GitMiner.logger.info("Mining estimate #{'%.2f' % percentage}%")
46
+ else
47
+ GitMiner.logger.info("Mining estimate #{'%.2f' % percentage}% (#{info.join(', ')})")
48
+ end
47
49
  end
48
50
  end
49
51
  end
@@ -0,0 +1,29 @@
1
+ require 'fileutils'
2
+
3
+ module GitMiner
4
+ class RegisterHook
5
+ FILENAME = ".git/hooks/post-commit"
6
+
7
+ class << self
8
+ def register(prefix:)
9
+ GitMiner.logger.info("Writing hook to #{FILENAME}")
10
+
11
+ if File.exists?(FILENAME)
12
+ File.open(FILENAME, 'a') do |file|
13
+ file.puts("")
14
+ end
15
+ else
16
+ FileUtils.touch(FILENAME)
17
+ FileUtils.chmod("+x", FILENAME)
18
+ end
19
+
20
+ File.open(FILENAME, 'a') do |file|
21
+ file.puts(
22
+ "# GitMiner hook",
23
+ "git mine #{prefix}"
24
+ )
25
+ end
26
+ end
27
+ end
28
+ end
29
+ end
@@ -1,3 +1,3 @@
1
1
  module GitMiner
2
- VERSION = "0.1.0"
2
+ VERSION = "0.2.3"
3
3
  end
data/lib/git_miner.rb CHANGED
@@ -4,5 +4,25 @@ Dir[File.join(__dir__, 'git_miner', '**', '*.rb')].each do |file|
4
4
  end
5
5
 
6
6
  module GitMiner
7
- class Error < StandardError; end
7
+ class UserError < StandardError; end
8
+
9
+ class << self
10
+ def logger
11
+ return @logger if defined?(@logger)
12
+
13
+ @logger = Logger.new(STDOUT)
14
+
15
+ @logger.formatter = proc do |severity, datetime, _progname, msg|
16
+ date_format = datetime.strftime("%Y-%m-%d %H:%M:%S")
17
+
18
+ if @logger.level == Logger::INFO
19
+ "[GitMiner] #{msg}\n"
20
+ else
21
+ "[GitMiner] #{date_format} #{severity}: #{msg}\n"
22
+ end
23
+ end
24
+
25
+ @logger
26
+ end
27
+ end
8
28
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: git_miner
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.0
4
+ version: 0.2.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - Thierry Joyal
8
- autorequire:
8
+ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2019-05-20 00:00:00.000000000 Z
11
+ date: 2022-01-30 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: parallel
@@ -58,14 +58,14 @@ dependencies:
58
58
  requirements:
59
59
  - - "~>"
60
60
  - !ruby/object:Gem::Version
61
- version: '10.0'
61
+ version: '13.0'
62
62
  type: :development
63
63
  prerelease: false
64
64
  version_requirements: !ruby/object:Gem::Requirement
65
65
  requirements:
66
66
  - - "~>"
67
67
  - !ruby/object:Gem::Version
68
- version: '10.0'
68
+ version: '13.0'
69
69
  - !ruby/object:Gem::Dependency
70
70
  name: rspec
71
71
  requirement: !ruby/object:Gem::Requirement
@@ -128,13 +128,14 @@ files:
128
128
  - lib/git_miner/group_manager.rb
129
129
  - lib/git_miner/mining_result.rb
130
130
  - lib/git_miner/progress.rb
131
+ - lib/git_miner/utils/register_hook.rb
131
132
  - lib/git_miner/version.rb
132
133
  homepage: https://github.com/tjoyal/git_miner
133
134
  licenses: []
134
135
  metadata:
135
136
  homepage_uri: https://github.com/tjoyal/git_miner
136
137
  source_code_uri: https://github.com/tjoyal/git_miner
137
- post_install_message:
138
+ post_install_message:
138
139
  rdoc_options: []
139
140
  require_paths:
140
141
  - lib
@@ -149,8 +150,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
149
150
  - !ruby/object:Gem::Version
150
151
  version: '0'
151
152
  requirements: []
152
- rubygems_version: 3.0.3
153
- signing_key:
153
+ rubygems_version: 3.2.32
154
+ signing_key:
154
155
  specification_version: 4
155
156
  summary: git-mine shell executable
156
157
  test_files: []