git-version-bump 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
data/.gitignore ADDED
@@ -0,0 +1,2 @@
1
+ .bundle
2
+ Gemfile.lock
data/Gemfile ADDED
@@ -0,0 +1,3 @@
1
+ source 'https://rubygems.org/'
2
+
3
+ gemspec
data/README.md ADDED
@@ -0,0 +1,82 @@
1
+ Maintain your program versions entirely within git. No local files
2
+ required!
3
+
4
+ This gem contains a set of Rake tasks and associated code to manage the
5
+ versioning of your code via git tags. No in-repo file is required to store
6
+ your version, which reduces unnecessary duplication of information.
7
+
8
+
9
+ # Usage
10
+
11
+ In your `Rakefile`, add the following line:
12
+
13
+ require 'git-version-bump/rake-tasks'
14
+
15
+ You will now have the following rake tasks available:
16
+
17
+ rake version:bump:major # bump major version (x.y.z -> x+1.0.0)
18
+ rake version:bump:minor # bump minor version (x.y.z -> x.y+1.0)
19
+ rake version:bump:patch # bump patch version (x.y.z -> x.y.z+1)
20
+
21
+ By running any of those, a new tag will be created representing the newly
22
+ incremented version number at the current commit. If no tags currently
23
+ exist, the previous version will be taken to be `0.0.0` and then incremented
24
+ accordingly.
25
+
26
+ To get access to this version information in your code (such as in your
27
+ `gemspec`, or the definition of a `::VERSION` constant), you can `require
28
+ 'git-version-bump'` and use the following methods:
29
+
30
+ GVB.version # Return the entire version string
31
+ GVB.major_version # Return just the 'major' portion of the version
32
+ GVB.minor_version # Return just the 'minor' portion of the version
33
+ GVB.patch_version # Return just the 'patch' portion of the version
34
+ GVB.internal_revision # Return "internal revision" information, or nil
35
+ GVB.date # Return the date of the most recent commit, or
36
+ # today's date if the tree is dirty
37
+
38
+ The "internal revision" is set when the tree is dirty, or when the latest
39
+ git commit doesn't correspond with a tag. In that case, the internal
40
+ revision will describe, in the manner of `git describe`, the full details of
41
+ the version of the code in use. This information will be part of the
42
+ version string provided by `gvb_version`.
43
+
44
+ If any of these methods are called when there isn't a tag or other version
45
+ information available, the version will be assumed to be `0.0.0.1.ENOTAG`
46
+ with a date of `1970-01-01`.
47
+
48
+
49
+ ## In your gemspec
50
+
51
+ Typically, you want to encode your version and commit date into your
52
+ gemspec, like this:
53
+
54
+ Gem::Specification.new do |s|
55
+ s.version = GVB.version
56
+ s.date = GVB.date
57
+
58
+ ...
59
+ end
60
+
61
+ The beauty of this method is that whenever you run a `rake build`, you'll
62
+ get a gem which is *accurately* versioned for the current state of your
63
+ repository. No more wondering if the `foobar-1.2.3` gem installed on your
64
+ system was built from pristine sources, or with that experimental patch you
65
+ were trying out...
66
+
67
+
68
+ ## In your gem
69
+
70
+ If, like me, you're one of those people who likes to be able to easily see
71
+ what version of a library I'm running, then you probably like to define a
72
+ `VERSION` constant somewhere in your gem's namespace. That, too, is simple
73
+ to do:
74
+
75
+ require 'git-version-bump'
76
+
77
+ class Foobar
78
+ VERSION = GVB.version
79
+ end
80
+
81
+ This will work correctly inside your git tree, and also in your installed
82
+ gem. Magical!
data/Rakefile ADDED
@@ -0,0 +1,21 @@
1
+ require 'rubygems'
2
+ require 'bundler'
3
+ require_relative 'lib/git-version-bump/rake-tasks'
4
+
5
+ begin
6
+ Bundler.setup(:default, :development)
7
+ rescue Bundler::BundlerError => e
8
+ $stderr.puts e.message
9
+ $stderr.puts "Run `bundle install` to install missing gems"
10
+ exit e.status_code
11
+ end
12
+
13
+ Bundler::GemHelper.install_tasks
14
+
15
+ require 'rdoc/task'
16
+
17
+ Rake::RDocTask.new do |rd|
18
+ rd.main = "README.md"
19
+ rd.title = 'git-version-bump'
20
+ rd.rdoc_files.include("README.md", "lib/**/*.rb")
21
+ end
@@ -0,0 +1,21 @@
1
+ require File.expand_path('../lib/git-version-bump', __FILE__)
2
+
3
+ Gem::Specification.new do |s|
4
+ s.name = "git-version-bump"
5
+
6
+ s.version = GVB.version
7
+ s.date = GVB.date
8
+
9
+ s.platform = Gem::Platform::RUBY
10
+
11
+ s.homepage = "http://theshed.hezmatt.org/git-version-bump"
12
+ s.summary = "Manage your app version entirely via git tags"
13
+ s.authors = ["Matt Palmer"]
14
+
15
+ s.extra_rdoc_files = ["README.md"]
16
+ s.files = `git ls-files`.split("\n")
17
+
18
+ s.add_development_dependency 'rake'
19
+ s.add_development_dependency 'bundler'
20
+ s.add_development_dependency 'rdoc'
21
+ end
@@ -0,0 +1,138 @@
1
+ module GitVersionBump
2
+ def self.version
3
+ git_ver = `git describe --dirty --match='v[0-9]*.[0-9]*.*[0-9]' 2>/dev/null`.
4
+ strip.
5
+ gsub(/^v/, '').
6
+ gsub('-', '.')
7
+
8
+ # If git returned success, then it gave us a described version.
9
+ # Success!
10
+ return git_ver if $? == 0
11
+
12
+ # git failed us; we're either not in a git repo or else we've never
13
+ # tagged anything before.
14
+
15
+ # Are we in a git repo with no tags? If so, dump out our
16
+ # super-special version and be done with it.
17
+ system("git status >/dev/null 2>&1")
18
+ return "0.0.0.1.ENOTAG" if $? == 0
19
+
20
+ # We're not in a git repo. This means that we need to get version
21
+ # information out of rubygems, given only the filename of who called
22
+ # us. This takes a little bit of effort.
23
+
24
+ if spec = GVB.caller_gemspec
25
+ return spec.version.to_s
26
+ else
27
+ # If we got here, something went *badly* wrong -- presumably, we
28
+ # weren't called from within a loaded gem, and so we've got *no*
29
+ # idea what's going on. Time to bail!
30
+ raise RuntimeError,
31
+ "GVB.version called from mysterious, non-gem location."
32
+ end
33
+ end
34
+
35
+ def self.major_version
36
+ ver = GVB.version
37
+ v = ver.split('.')[0]
38
+
39
+ unless v =~ /^[0-9]+$/
40
+ raise ArgumentError,
41
+ "#{v} (part of #{ver.inspect}) is not a numeric version component. Abandon ship!"
42
+ end
43
+
44
+ return v.to_i
45
+ end
46
+
47
+ def self.minor_version
48
+ ver = GVB.version
49
+ v = ver.split('.')[1]
50
+
51
+ unless v =~ /^[0-9]+$/
52
+ raise ArgumentError,
53
+ "#{v} (part of #{ver.inspect}) is not a numeric version component. Abandon ship!"
54
+ end
55
+
56
+ return v.to_i
57
+ end
58
+
59
+ def self.patch_version
60
+ ver = GVB.version
61
+ v = ver.split('.')[2]
62
+
63
+ unless v =~ /^[0-9]+$/
64
+ raise ArgumentError,
65
+ "#{v} (part of #{ver.inspect}) is not a numeric version component. Abandon ship!"
66
+ end
67
+
68
+ return v.to_i
69
+ end
70
+
71
+ def self.internal_revision
72
+ GVB.version.split('.', 4)[3].to_s
73
+ end
74
+
75
+ def self.date
76
+ # Are we in a git tree?
77
+ system("git status >/dev/null 2>&1")
78
+ if $? == 0
79
+ # Yes, we're in git.
80
+
81
+ if GVB.dirty_tree?
82
+ return Time.now.strftime("%F")
83
+ else
84
+ # Clean tree. Date of last commit is needed.
85
+ return `git show --format=format:%ad --date=short | head -n 1`.strip
86
+ end
87
+ else
88
+ # Not in git; time to hit the gemspecs
89
+ if spec = GVB.caller_gemspec
90
+ return spec.version.to_s
91
+ else
92
+ raise RuntimeError,
93
+ "GVB.date called from mysterious, non-gem location."
94
+ end
95
+ end
96
+ end
97
+
98
+ def self.tag_version(v)
99
+ if GVB.dirty_tree?
100
+ puts "You have uncommitted files. Refusing to tag a dirty tree."
101
+ else
102
+ puts "Tagging version #{v}..."
103
+ system("git tag -a -m 'Version v#{v}' v#{v}")
104
+ end
105
+ end
106
+
107
+ def self.caller_gemspec
108
+ # First up, who called us? Because this method gets called from other
109
+ # methods within this file, we can't just look at Gem.location_of_caller,
110
+ # but instead we need to parse the whole caller stack ourselves.
111
+ caller_file = caller.
112
+ map { |l| l.split(':')[0] }.
113
+ find { |l| l != __FILE__ }
114
+
115
+ # Next we grovel through all the loaded gems to try and find the gem
116
+ # that contains the caller's file.
117
+ Gem.loaded_specs.values.each do |spec|
118
+ if Dir.
119
+ glob(spec.lib_dirs_glob).
120
+ find { |d| caller_file.index(d) == 0 }
121
+ # The caller_file is in this
122
+ # gem! Woohoo!
123
+ return spec
124
+ end
125
+ end
126
+
127
+ nil
128
+ end
129
+
130
+ def self.dirty_tree?
131
+ # Are we in a dirty, dirty tree?
132
+ system("! git diff --no-ext-diff --quiet --exit-code || ! git diff-index --cached --quiet HEAD")
133
+
134
+ $? == 0
135
+ end
136
+ end
137
+
138
+ GVB = GitVersionBump
@@ -0,0 +1,26 @@
1
+ require_relative '../git-version-bump'
2
+
3
+ namespace :version do
4
+ namespace :bump do
5
+ desc "bump major version (x.y.z -> x+1.0.0)"
6
+ task :major do
7
+ GVB.tag_version "#{GVB.major_version + 1}.0.0"
8
+
9
+ puts "Version is now #{GVB.version}"
10
+ end
11
+
12
+ desc "bump minor version (x.y.z -> x.y+1.0)"
13
+ task :minor do
14
+ GVB.tag_version "#{GVB.major_version}.#{GVB.minor_version+1}.0"
15
+
16
+ puts "Version is now #{GVB.version}"
17
+ end
18
+
19
+ desc "bump patch version (x.y.z -> x.y.z+1)"
20
+ task :patch do
21
+ GVB.tag_version "#{GVB.major_version}.#{GVB.minor_version}.#{GVB.patch_version+1}"
22
+
23
+ puts "Version is now #{GVB.version}"
24
+ end
25
+ end
26
+ end
metadata ADDED
@@ -0,0 +1,106 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: git-version-bump
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - Matt Palmer
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2014-02-11 00:00:00.000000000 Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ name: rake
16
+ requirement: !ruby/object:Gem::Requirement
17
+ none: false
18
+ requirements:
19
+ - - ! '>='
20
+ - !ruby/object:Gem::Version
21
+ version: '0'
22
+ type: :development
23
+ prerelease: false
24
+ version_requirements: !ruby/object:Gem::Requirement
25
+ none: false
26
+ requirements:
27
+ - - ! '>='
28
+ - !ruby/object:Gem::Version
29
+ version: '0'
30
+ - !ruby/object:Gem::Dependency
31
+ name: bundler
32
+ requirement: !ruby/object:Gem::Requirement
33
+ none: false
34
+ requirements:
35
+ - - ! '>='
36
+ - !ruby/object:Gem::Version
37
+ version: '0'
38
+ type: :development
39
+ prerelease: false
40
+ version_requirements: !ruby/object:Gem::Requirement
41
+ none: false
42
+ requirements:
43
+ - - ! '>='
44
+ - !ruby/object:Gem::Version
45
+ version: '0'
46
+ - !ruby/object:Gem::Dependency
47
+ name: rdoc
48
+ requirement: !ruby/object:Gem::Requirement
49
+ none: false
50
+ requirements:
51
+ - - ! '>='
52
+ - !ruby/object:Gem::Version
53
+ version: '0'
54
+ type: :development
55
+ prerelease: false
56
+ version_requirements: !ruby/object:Gem::Requirement
57
+ none: false
58
+ requirements:
59
+ - - ! '>='
60
+ - !ruby/object:Gem::Version
61
+ version: '0'
62
+ description:
63
+ email:
64
+ executables: []
65
+ extensions: []
66
+ extra_rdoc_files:
67
+ - README.md
68
+ files:
69
+ - .gitignore
70
+ - Gemfile
71
+ - README.md
72
+ - Rakefile
73
+ - git-version-bump.gemspec
74
+ - lib/git-version-bump.rb
75
+ - lib/git-version-bump/rake-tasks.rb
76
+ homepage: http://theshed.hezmatt.org/git-version-bump
77
+ licenses: []
78
+ post_install_message:
79
+ rdoc_options: []
80
+ require_paths:
81
+ - lib
82
+ required_ruby_version: !ruby/object:Gem::Requirement
83
+ none: false
84
+ requirements:
85
+ - - ! '>='
86
+ - !ruby/object:Gem::Version
87
+ version: '0'
88
+ segments:
89
+ - 0
90
+ hash: 4544833629882770877
91
+ required_rubygems_version: !ruby/object:Gem::Requirement
92
+ none: false
93
+ requirements:
94
+ - - ! '>='
95
+ - !ruby/object:Gem::Version
96
+ version: '0'
97
+ segments:
98
+ - 0
99
+ hash: 4544833629882770877
100
+ requirements: []
101
+ rubyforge_project:
102
+ rubygems_version: 1.8.23
103
+ signing_key:
104
+ specification_version: 3
105
+ summary: Manage your app version entirely via git tags
106
+ test_files: []