releasetool 0.2.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 +7 -0
- data/.gitignore +18 -0
- data/Gemfile +4 -0
- data/LICENSE.txt +22 -0
- data/README.md +94 -0
- data/Rakefile +6 -0
- data/bin/release +5 -0
- data/lib/releasetool.rb +5 -0
- data/lib/releasetool/release.rb +81 -0
- data/lib/releasetool/util.rb +23 -0
- data/lib/releasetool/version.rb +55 -0
- data/lib/tasks/release_thor.rb +119 -0
- data/release_notes/__TEMPLATE__.md +4 -0
- data/release_notes/v0.0.1.md +4 -0
- data/release_notes/v0.0.2.md +9 -0
- data/release_notes/v0.0.3.md +6 -0
- data/release_notes/v0.1.0.md +8 -0
- data/release_notes/v0.1.1.md +6 -0
- data/release_notes/v0.2.0.md +6 -0
- data/releasetool.gemspec +26 -0
- data/spec/fixtures/example_with_releases.tar +0 -0
- data/spec/releasetool_spec.rb +141 -0
- data/spec/spec_helper.rb +17 -0
- data/spec/version_spec.rb +75 -0
- metadata +128 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA256:
|
3
|
+
metadata.gz: 1b0af76c63ee063f38c88599f766cb05f3d139e2048a7e694175778c5f84c43f
|
4
|
+
data.tar.gz: e145cda46f5b692a06ad962c4642636d57c5f86a68f9b5d275b418128edf035a
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: ed316d721bfebcd8a7e5a3bc7f0c43d866634ce4ffd3f8e9e00b66ac5004bfcc38a0d88c23c327a245b7a6a60da3592ad83bd7a9af96a80d71afcd679d712b6c
|
7
|
+
data.tar.gz: 0d6652d10950881d889ac7e3ddd7d10fca6c312e1868ce2882eb97ddab068f59633339187e577634b23e22e1e1a05a7ee3977f1480bf20996adaf7c77f68f579
|
data/.gitignore
ADDED
data/Gemfile
ADDED
data/LICENSE.txt
ADDED
@@ -0,0 +1,22 @@
|
|
1
|
+
Copyright (c) 2014 Tim Diggins
|
2
|
+
|
3
|
+
MIT License
|
4
|
+
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
6
|
+
a copy of this software and associated documentation files (the
|
7
|
+
"Software"), to deal in the Software without restriction, including
|
8
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
9
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
10
|
+
permit persons to whom the Software is furnished to do so, subject to
|
11
|
+
the following conditions:
|
12
|
+
|
13
|
+
The above copyright notice and this permission notice shall be
|
14
|
+
included in all copies or substantial portions of the Software.
|
15
|
+
|
16
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
17
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
18
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
19
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
20
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
21
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
22
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,94 @@
|
|
1
|
+
# Releasetool
|
2
|
+
|
3
|
+
We use this tool to create releases and their documentation.
|
4
|
+
It makes versioned/numbered deployments easier to track.
|
5
|
+
Would possibly be nice if there was an engine to display the release notes in a rails app as well.
|
6
|
+
|
7
|
+
Not quite one-click release, but getting there...
|
8
|
+
|
9
|
+
## Installation
|
10
|
+
|
11
|
+
Add this line to your application's Gemfile:
|
12
|
+
|
13
|
+
gem 'releasetool'
|
14
|
+
|
15
|
+
And then execute:
|
16
|
+
|
17
|
+
$ bundle
|
18
|
+
|
19
|
+
Or install it yourself as:
|
20
|
+
|
21
|
+
$ gem install releasetool
|
22
|
+
|
23
|
+
## Usage
|
24
|
+
|
25
|
+
### List existing tags
|
26
|
+
|
27
|
+
```release list```
|
28
|
+
|
29
|
+
### Start the release -- generate release notes and update version file
|
30
|
+
|
31
|
+
```release start```
|
32
|
+
|
33
|
+
This will start a new patch verison, but you can start minor or major
|
34
|
+
|
35
|
+
```release start --minor```
|
36
|
+
|
37
|
+
```release start --major```
|
38
|
+
|
39
|
+
Or you can specify the new verison.
|
40
|
+
|
41
|
+
```release start NEW_VERSION```
|
42
|
+
|
43
|
+
All of these will use the most recent tag as the previous version. If you don't have a most recent tag, or you want to start from something else use:
|
44
|
+
|
45
|
+
```release start -s PREVIOUS_VERSION NEW_VERSION```
|
46
|
+
|
47
|
+
Now edit the created release notes (release_notes/NEW_VERSION.md)
|
48
|
+
|
49
|
+
### Commit release notes
|
50
|
+
|
51
|
+
```release commit```
|
52
|
+
|
53
|
+
Currently this also commits config/initializers/00-version.rb as this is handy for our rails projects. Might move this out into a config (or make check for the existings of , but only if need this to span non-rails projects.
|
54
|
+
|
55
|
+
### Create a named tag (for later reference using release list)
|
56
|
+
|
57
|
+
```release tag```
|
58
|
+
|
59
|
+
It will ask for a one-line summary of the release (full details are in the release notes)
|
60
|
+
|
61
|
+
### Push commits and tag
|
62
|
+
|
63
|
+
```release push```
|
64
|
+
|
65
|
+
|
66
|
+
## Testing
|
67
|
+
|
68
|
+
The tests work on a known-good repo stored in `spec/fixtures/example_with_releases.tar`. To recreate this:
|
69
|
+
```
|
70
|
+
cd spec/fixtures/example_with_releases && tar -xvf ../example_with_releases.tar && cd -
|
71
|
+
```
|
72
|
+
|
73
|
+
then you can tweak it and save it back with:
|
74
|
+
```
|
75
|
+
cd spec/fixtures/example_with_releases && tar -cvf ../example_with_releases.tar . && cd -
|
76
|
+
```
|
77
|
+
|
78
|
+
## Configuration
|
79
|
+
|
80
|
+
If you want it to automatically update the version number in a string then set the environment variable
|
81
|
+
`RELEASETOOL_VERSION_FILE`, eg. `export RELEASETOOL_VERSION_FILE=./lib/releasetool.rb`. By default this is configured to config/initializers/00-version.rb (useful for rails projects).
|
82
|
+
|
83
|
+
|
84
|
+
## Contributing
|
85
|
+
|
86
|
+
see testing above
|
87
|
+
|
88
|
+
1. Fork it
|
89
|
+
2. Create your feature branch (`git checkout -b my-new-feature`)
|
90
|
+
3. Commit your changes (`git commit -am 'Add some feature'`)
|
91
|
+
4. Push to the branch (`git push origin my-new-feature`)
|
92
|
+
5. Create new Pull Request
|
93
|
+
|
94
|
+
For releasing the releasetool itself we need to set an environment variable `export RELEASETOOL_VERSION_FILE=./lib/releasetool/version.rb`
|
data/Rakefile
ADDED
data/bin/release
ADDED
data/lib/releasetool.rb
ADDED
@@ -0,0 +1,81 @@
|
|
1
|
+
require "releasetool/util"
|
2
|
+
|
3
|
+
module Releasetool
|
4
|
+
class Release
|
5
|
+
include Releasetool::Util
|
6
|
+
|
7
|
+
def initialize(version, previous:)
|
8
|
+
raise "Version must be a Releasetool::Version" unless version.is_a?(Releasetool::Version)
|
9
|
+
if previous
|
10
|
+
raise "Previous must be nil or a Releasetool::Version" unless version.is_a?(Releasetool::Version)
|
11
|
+
end
|
12
|
+
@version = version
|
13
|
+
@previous = previous
|
14
|
+
end
|
15
|
+
|
16
|
+
def prepare(edit: false)
|
17
|
+
puts headers
|
18
|
+
commits = `git log #{@previous}..HEAD --pretty=format:"- %B"`
|
19
|
+
notes = commits.gsub("\n\n", "\n")
|
20
|
+
notes_file = "#{DIR}/#{@version}.md"
|
21
|
+
if File.exists?(notes_file)
|
22
|
+
puts "-"*80
|
23
|
+
puts " File '#{notes_file}' already exists (appending)"
|
24
|
+
puts "-"*80
|
25
|
+
File.open(notes_file, 'a') do |f|
|
26
|
+
f.puts("\n\nAPPENDED:\n\n")
|
27
|
+
f.puts(notes)
|
28
|
+
end
|
29
|
+
else
|
30
|
+
ensure_dir
|
31
|
+
File.open(notes_file, 'w') do |f|
|
32
|
+
f.puts(headers)
|
33
|
+
f.puts(notes)
|
34
|
+
end
|
35
|
+
puts "written to #{notes_file}"
|
36
|
+
if edit
|
37
|
+
system("open #{notes_file}")
|
38
|
+
end
|
39
|
+
end
|
40
|
+
if File.exists?(VERSION_FILE)
|
41
|
+
from_version = @previous.to_s_without_v
|
42
|
+
to_version = @version.to_s_without_v
|
43
|
+
guarded_system("cat #{VERSION_FILE} | sed s/#{from_version}/#{to_version.gsub('.', '\.')}/ > #{VERSION_FILE}.tmp")
|
44
|
+
guarded_system("mv #{VERSION_FILE}.tmp #{VERSION_FILE}")
|
45
|
+
end
|
46
|
+
end
|
47
|
+
|
48
|
+
private
|
49
|
+
|
50
|
+
def ensure_dir
|
51
|
+
Dir.mkdir(DIR) unless File.exists?(DIR)
|
52
|
+
end
|
53
|
+
|
54
|
+
def headers
|
55
|
+
@headers ||= template.gsub("$VERSION", @version.to_s).gsub("$PREVIOUS", @previous.to_s)
|
56
|
+
end
|
57
|
+
|
58
|
+
def template
|
59
|
+
File.read(ensured_template_file)
|
60
|
+
end
|
61
|
+
|
62
|
+
def ensured_template_file
|
63
|
+
ensure_dir
|
64
|
+
template_file = "#{DIR}/#{TEMPLATE_FILE}"
|
65
|
+
create_template_file(template_file) unless File.exists?(template_file)
|
66
|
+
template_file
|
67
|
+
end
|
68
|
+
|
69
|
+
def create_template_file(template_file)
|
70
|
+
File.open(template_file, "w") do |f|
|
71
|
+
f.write <<~FILEEND
|
72
|
+
$VERSION Release Notes
|
73
|
+
|
74
|
+
*Changes since $PREVIOUS*
|
75
|
+
|
76
|
+
FILEEND
|
77
|
+
end
|
78
|
+
end
|
79
|
+
|
80
|
+
end
|
81
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
module Releasetool
|
2
|
+
module Util
|
3
|
+
|
4
|
+
DIR = "release_notes"
|
5
|
+
VERSION_FILE = ENV['RELEASETOOL_VERSION_FILE'] || "config/initializers/00-version.rb" #rails out of box
|
6
|
+
TEMPLATE_FILE = "__TEMPLATE__.md" # relative to DIR
|
7
|
+
RELEASE_MARKER_FILE = ".RELEASE_NEW_VERSION" # should be a config var
|
8
|
+
|
9
|
+
def stored_version
|
10
|
+
fail Thor::Error.new("No stored version... did you forget to do release start?") unless File.exist?(RELEASE_MARKER_FILE)
|
11
|
+
File.read(RELEASE_MARKER_FILE).strip
|
12
|
+
end
|
13
|
+
|
14
|
+
def remove_stored_version
|
15
|
+
guarded_system("rm #{RELEASE_MARKER_FILE}") if File.exist?(RELEASE_MARKER_FILE)
|
16
|
+
end
|
17
|
+
|
18
|
+
def guarded_system(command)
|
19
|
+
puts command
|
20
|
+
system(command) or raise Thor::Error.new("Couldn't '#{command}'")
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,55 @@
|
|
1
|
+
module Releasetool
|
2
|
+
class Version
|
3
|
+
attr_reader :ident
|
4
|
+
def initialize(ident)
|
5
|
+
raise "Not a valid version identifier: #{ident.inspect}" unless ident.is_a?(String)
|
6
|
+
@ident = ident
|
7
|
+
end
|
8
|
+
|
9
|
+
def next_patch
|
10
|
+
self.class.normalized(segments[0], segments[1], incremented(segments[2]))
|
11
|
+
end
|
12
|
+
|
13
|
+
def next_minor
|
14
|
+
self.class.normalized(segments[0], incremented(segments[1]), 0)
|
15
|
+
end
|
16
|
+
|
17
|
+
def next_major
|
18
|
+
self.class.normalized(incremented(segments[0]), 0, 0)
|
19
|
+
end
|
20
|
+
|
21
|
+
def to_s
|
22
|
+
if @ident[0] == "v"
|
23
|
+
@ident
|
24
|
+
else
|
25
|
+
"v#{@ident}"
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
def to_s_without_v
|
30
|
+
if @ident[0] == "v"
|
31
|
+
@ident[1..-1]
|
32
|
+
else
|
33
|
+
@ident
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
def ==(other)
|
38
|
+
other.is_a?(Releasetool::Version) && ident == other.ident
|
39
|
+
end
|
40
|
+
|
41
|
+
def self.normalized(major, minor, patch)
|
42
|
+
new("v#{major}.#{minor}.#{patch}")
|
43
|
+
end
|
44
|
+
|
45
|
+
private
|
46
|
+
def incremented(v)
|
47
|
+
raise "Can't work out next version from #{self}" unless v.to_i.to_s == v
|
48
|
+
v.to_i + 1
|
49
|
+
end
|
50
|
+
|
51
|
+
def segments
|
52
|
+
@segments ||= to_s_without_v.split(".")
|
53
|
+
end
|
54
|
+
end
|
55
|
+
end
|
@@ -0,0 +1,119 @@
|
|
1
|
+
require 'thor'
|
2
|
+
require "releasetool/release"
|
3
|
+
require "releasetool/util"
|
4
|
+
require "releasetool/version"
|
5
|
+
|
6
|
+
class Release < Thor
|
7
|
+
|
8
|
+
include Releasetool::Util
|
9
|
+
desc "list", <<-END
|
10
|
+
show a list of tags ordered by date (just a git listing).
|
11
|
+
END
|
12
|
+
|
13
|
+
def list
|
14
|
+
system("git for-each-ref --sort='*authordate' --format='%(taggerdate:short) | %(tag) | %(contents)' refs/tags")
|
15
|
+
end
|
16
|
+
|
17
|
+
# ========================
|
18
|
+
|
19
|
+
desc "latest", <<-END
|
20
|
+
output the latest version (tag)
|
21
|
+
END
|
22
|
+
|
23
|
+
def latest
|
24
|
+
puts previous_version
|
25
|
+
end
|
26
|
+
|
27
|
+
# ========================
|
28
|
+
|
29
|
+
desc "log", <<-END
|
30
|
+
output the latest version (tag)
|
31
|
+
END
|
32
|
+
|
33
|
+
def log(*args)
|
34
|
+
extra = " #{args.join(" ")}" if args.length > 0
|
35
|
+
guarded_system("git log #{previous_version}..#{extra}")
|
36
|
+
end
|
37
|
+
|
38
|
+
# ========================
|
39
|
+
|
40
|
+
method_option :since, type: :string, desc: "since commit_ref (or will use most recent tag)", required: false,
|
41
|
+
aliases: 's'
|
42
|
+
method_option :edit, type: :boolean, desc: "edit", required: false, aliases: 'e'
|
43
|
+
method_option :minor, type: :boolean, desc: "minor version", required: false, default: false
|
44
|
+
|
45
|
+
desc "start (NEW_VERSION)", <<-END
|
46
|
+
Start a release by doing a prepare, and storing the target release in #{RELEASE_MARKER_FILE}.
|
47
|
+
END
|
48
|
+
|
49
|
+
def start(specified_version=nil)
|
50
|
+
if File.exists?(RELEASE_MARKER_FILE)
|
51
|
+
raise Thor::Error.new("Can't start when already started on a version. release abort or release finish")
|
52
|
+
end
|
53
|
+
version = next_version(specified_version)
|
54
|
+
File.open(RELEASE_MARKER_FILE, 'w') do |f|
|
55
|
+
f.write(version)
|
56
|
+
end
|
57
|
+
Releasetool::Release.new(version, previous: previous_version).prepare(edit: options[:edit])
|
58
|
+
end
|
59
|
+
|
60
|
+
DEFAULT_COMMIT_MESSAGE = 'preparing for release [CI SKIP]'
|
61
|
+
desc "commit (NEW_VERSION)", <<-END
|
62
|
+
Commit release and version identifier to git with message '#{DEFAULT_COMMIT_MESSAGE}'.
|
63
|
+
If no version given, it will use the version stored by release start
|
64
|
+
END
|
65
|
+
|
66
|
+
def commit(version=nil)
|
67
|
+
version ||= stored_version
|
68
|
+
guarded_system("git add #{DIR}")
|
69
|
+
guarded_system("git add #{VERSION_FILE}") if File.exists?(VERSION_FILE)
|
70
|
+
guarded_system("git commit #{DIR} #{File.exists?(VERSION_FILE) ? VERSION_FILE : ''} -e -m\"#{DEFAULT_COMMIT_MESSAGE}\"")
|
71
|
+
end
|
72
|
+
|
73
|
+
desc "tag (NEW_VERSION)", <<-END
|
74
|
+
Tag release.
|
75
|
+
If no version given, it will use the version stored by release start
|
76
|
+
END
|
77
|
+
|
78
|
+
def tag(version=nil)
|
79
|
+
version ||= stored_version
|
80
|
+
guarded_system("git tag -a #{version}")
|
81
|
+
end
|
82
|
+
|
83
|
+
desc "push (NEW_VERSION)", <<-END
|
84
|
+
pushes current branch and tag
|
85
|
+
If no version given, it will use the version stored by release start.
|
86
|
+
END
|
87
|
+
|
88
|
+
def push(version=nil)
|
89
|
+
version ||= stored_version
|
90
|
+
guarded_system("git push")
|
91
|
+
guarded_system("git push origin #{version}")
|
92
|
+
remove_stored_version
|
93
|
+
end
|
94
|
+
|
95
|
+
desc "abort", <<-END
|
96
|
+
throws away the version stored by release start.
|
97
|
+
END
|
98
|
+
|
99
|
+
def abort
|
100
|
+
remove_stored_version
|
101
|
+
end
|
102
|
+
|
103
|
+
protected
|
104
|
+
|
105
|
+
def next_version(specified)
|
106
|
+
return Releasetool::Version.new(specified) if specified
|
107
|
+
if options[:major]
|
108
|
+
previous_version.next_major
|
109
|
+
elsif options[:minor]
|
110
|
+
previous_version.next_minor
|
111
|
+
else
|
112
|
+
previous_version.next_patch
|
113
|
+
end
|
114
|
+
end
|
115
|
+
|
116
|
+
def previous_version
|
117
|
+
Releasetool::Version.new(options[:since] || `git describe --abbrev=0 --tags`.strip)
|
118
|
+
end
|
119
|
+
end
|
@@ -0,0 +1,6 @@
|
|
1
|
+
v0.2.0 Release Notes
|
2
|
+
|
3
|
+
*Changes since v0.1.1*
|
4
|
+
|
5
|
+
- use explicit template file: You can edit the template that is used for new release_notes (it will be created within the folder next time you do release start)
|
6
|
+
- append when already present (if the file already exists then release start / release prepare will add the commit history to the file rather than just printing it out)
|
data/releasetool.gemspec
ADDED
@@ -0,0 +1,26 @@
|
|
1
|
+
# coding: utf-8
|
2
|
+
lib = File.expand_path('../lib', __FILE__)
|
3
|
+
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
4
|
+
require 'releasetool'
|
5
|
+
|
6
|
+
Gem::Specification.new do |spec|
|
7
|
+
spec.name = "releasetool"
|
8
|
+
spec.version = Releasetool::VERSION
|
9
|
+
spec.authors = ["Tim Diggins"]
|
10
|
+
spec.email = ["tim@red56.co.uk"]
|
11
|
+
spec.description = %q{Some release-related functions, initially just release notes management and creation}
|
12
|
+
spec.summary = %q{Release management tools}
|
13
|
+
spec.homepage = ""
|
14
|
+
spec.license = "MIT"
|
15
|
+
|
16
|
+
spec.files = `git ls-files`.split($/)
|
17
|
+
spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
|
18
|
+
spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
|
19
|
+
spec.require_paths = ["lib"]
|
20
|
+
|
21
|
+
spec.add_dependency 'thor', '~> 0.18'
|
22
|
+
|
23
|
+
spec.add_development_dependency "bundler", "~> 1.3"
|
24
|
+
spec.add_development_dependency "rake"
|
25
|
+
spec.add_development_dependency "rspec"
|
26
|
+
end
|
Binary file
|
@@ -0,0 +1,141 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
require 'fileutils'
|
3
|
+
require File.expand_path('../../lib/tasks/release_thor', __FILE__)
|
4
|
+
|
5
|
+
describe Releasetool do
|
6
|
+
it 'should have a version number' do
|
7
|
+
expect(Releasetool::VERSION).not_to be_nil
|
8
|
+
end
|
9
|
+
end
|
10
|
+
|
11
|
+
describe Release, quietly: true do
|
12
|
+
subject { Release.new }
|
13
|
+
TMPDIR = File.expand_path('../../tmp/testing', __FILE__)
|
14
|
+
ROOT_DIR = File.expand_path('../..', __FILE__)
|
15
|
+
before {
|
16
|
+
FileUtils.rmtree(TMPDIR)
|
17
|
+
FileUtils.mkdir_p(TMPDIR)
|
18
|
+
FileUtils.chdir(TMPDIR)
|
19
|
+
system('tar -xf ../../spec/fixtures/example_with_releases.tar')
|
20
|
+
}
|
21
|
+
after {
|
22
|
+
FileUtils.chdir(ROOT_DIR)
|
23
|
+
}
|
24
|
+
it "should respond to list" do
|
25
|
+
subject.list
|
26
|
+
end
|
27
|
+
|
28
|
+
let(:mock_target){ instance_double(Releasetool::Release)}
|
29
|
+
let(:v_0_0_1) {Releasetool::Version.new("v0.0.1")}
|
30
|
+
let(:v_0_0_2) {Releasetool::Version.new("v0.0.2")}
|
31
|
+
let(:v_0_0_3) {Releasetool::Version.new("v0.0.3")}
|
32
|
+
let(:v_0_1_0) {Releasetool::Version.new("v0.1.0")}
|
33
|
+
let(:v_1_0_0) {Releasetool::Version.new("v1.0.0")}
|
34
|
+
|
35
|
+
context "start" do
|
36
|
+
context "with a since" do
|
37
|
+
subject { Release.new([], {since: 'v0.0.2'}, {}) }
|
38
|
+
it "it should do a prepare and store a file" do
|
39
|
+
expect(Releasetool::Release).to receive(:new).with(v_0_0_3, previous: v_0_0_2).and_return(mock_target)
|
40
|
+
expect(mock_target).to receive(:prepare)
|
41
|
+
subject.start('v0.0.3')
|
42
|
+
end
|
43
|
+
it "stores a release-version file" do
|
44
|
+
allow(Releasetool::Release).to receive(:new).with(v_0_0_3, previous: v_0_0_2).and_return(mock_target)
|
45
|
+
allow(mock_target).to receive(:prepare)
|
46
|
+
expect { subject.start('v0.0.3') }.to change {
|
47
|
+
File.exist?(File.join(TMPDIR, '.RELEASE_NEW_VERSION'))
|
48
|
+
}
|
49
|
+
expect(File.read(File.join(TMPDIR, '.RELEASE_NEW_VERSION')).to_s).to eq('v0.0.3')
|
50
|
+
end
|
51
|
+
|
52
|
+
it "with existing release-version file, it should freak out" do
|
53
|
+
FileUtils.touch(File.join(TMPDIR, '.RELEASE_NEW_VERSION'))
|
54
|
+
expect { subject.start('v0.0.3') }.to raise_error
|
55
|
+
end
|
56
|
+
end
|
57
|
+
|
58
|
+
context "without a since" do
|
59
|
+
it "it should use latest tag" do
|
60
|
+
expect(Releasetool::Release).to receive(:new).with(v_0_0_3, previous: v_0_0_1).and_return(mock_target)
|
61
|
+
expect(mock_target).to receive(:prepare)
|
62
|
+
subject.start('v0.0.3')
|
63
|
+
end
|
64
|
+
end
|
65
|
+
|
66
|
+
context "without a new version" do
|
67
|
+
it "it should use next patch level" do
|
68
|
+
expect(Releasetool::Release).to receive(:new).with(v_0_0_2, previous: v_0_0_1).and_return(mock_target)
|
69
|
+
expect(mock_target).to receive(:prepare)
|
70
|
+
subject.start
|
71
|
+
end
|
72
|
+
end
|
73
|
+
|
74
|
+
context "without a new version but with --minor modifier" do
|
75
|
+
subject { Release.new([], {minor: true}, {}) }
|
76
|
+
|
77
|
+
it "it should use next minor level" do
|
78
|
+
expect(Releasetool::Release).to receive(:new).with(v_0_1_0, previous: v_0_0_1).and_return(mock_target)
|
79
|
+
expect(mock_target).to receive(:prepare)
|
80
|
+
subject.start
|
81
|
+
end
|
82
|
+
end
|
83
|
+
|
84
|
+
context "without a new version but with --major modifier" do
|
85
|
+
subject { Release.new([], {major: true}, {}) }
|
86
|
+
|
87
|
+
it "it should use next minor level" do
|
88
|
+
expect(Releasetool::Release).to receive(:new).with(v_1_0_0, previous: v_0_0_1).and_return(mock_target)
|
89
|
+
expect(mock_target).to receive(:prepare)
|
90
|
+
subject.start
|
91
|
+
end
|
92
|
+
end
|
93
|
+
end
|
94
|
+
|
95
|
+
describe "latest" do
|
96
|
+
it "outputs latest version" do
|
97
|
+
expect{subject.latest}.to output("v0.0.1\n").to_stdout
|
98
|
+
end
|
99
|
+
end
|
100
|
+
|
101
|
+
describe "log" do
|
102
|
+
it "executes correct git log code" do
|
103
|
+
expect(subject).to receive(:guarded_system).with("git log v0.0.1..")
|
104
|
+
subject.log
|
105
|
+
end
|
106
|
+
|
107
|
+
it "allow other args" do
|
108
|
+
expect(subject).to receive(:guarded_system).with("git log v0.0.1.. --stat --reverse")
|
109
|
+
subject.log("--stat", "--reverse")
|
110
|
+
end
|
111
|
+
end
|
112
|
+
|
113
|
+
|
114
|
+
# describe 'CLI' do
|
115
|
+
# it "should work with source and no target" do
|
116
|
+
# puts "CLI"
|
117
|
+
# puts "PWD: #{`pwd`}"
|
118
|
+
# system('cat config/initializers/00-version.rb')
|
119
|
+
# expect(capture(:stderr) {
|
120
|
+
# Release.start(%w[prepare -s v0.0.2 v0.0.3"])
|
121
|
+
# }.strip).to eq('')
|
122
|
+
# end
|
123
|
+
# it "should not work with no target" do
|
124
|
+
# expect(capture(:stderr) {
|
125
|
+
# Release.start(%w[prepare -s v0.0.2"])
|
126
|
+
# }.strip).not_to eq('')
|
127
|
+
# end
|
128
|
+
# it "should not work with no source" do
|
129
|
+
# expect(capture(:stderr) {
|
130
|
+
# Release.start(%w[flong v0.0.3"])
|
131
|
+
# }.strip).not_to eq('')
|
132
|
+
# end
|
133
|
+
#
|
134
|
+
# it "should not work with no args" do
|
135
|
+
# expect(capture(:stderr) {
|
136
|
+
# Release.start(%w[prepare"])
|
137
|
+
# }.strip).not_to eq('')
|
138
|
+
# end
|
139
|
+
# end
|
140
|
+
|
141
|
+
end
|
data/spec/spec_helper.rb
ADDED
@@ -0,0 +1,17 @@
|
|
1
|
+
$LOAD_PATH.unshift File.expand_path('../../lib', __FILE__)
|
2
|
+
require 'releasetool'
|
3
|
+
|
4
|
+
RSpec.configure do |config|
|
5
|
+
config.around quietly: true do |example|
|
6
|
+
RSpec.configure do |config|
|
7
|
+
original_stderr = $stderr
|
8
|
+
original_stdout = $stdout
|
9
|
+
# Redirect stderr and stdout
|
10
|
+
$stderr = File.open(File::NULL, "w")
|
11
|
+
$stdout = File.open(File::NULL, "w")
|
12
|
+
example.run
|
13
|
+
$stderr = original_stderr
|
14
|
+
$stdout = original_stdout
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
@@ -0,0 +1,75 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
require "releasetool/version"
|
4
|
+
describe Releasetool::Version do
|
5
|
+
describe "to_s" do
|
6
|
+
it "includes v" do
|
7
|
+
expect(Releasetool::Version.new("v1.2.3").to_s).to eq("v1.2.3")
|
8
|
+
end
|
9
|
+
it "includes v even if not given" do
|
10
|
+
expect(Releasetool::Version.new("1.2.3").to_s).to eq("v1.2.3")
|
11
|
+
end
|
12
|
+
end
|
13
|
+
|
14
|
+
describe "to_s_without_v" do
|
15
|
+
it "strips" do
|
16
|
+
expect(Releasetool::Version.new("v1.2.3").to_s_without_v).to eq("1.2.3")
|
17
|
+
end
|
18
|
+
it "works without" do
|
19
|
+
expect(Releasetool::Version.new("1.2.3").to_s_without_v).to eq("1.2.3")
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
describe "next_patch" do
|
24
|
+
let(:v_0_0_1) {Releasetool::Version.new("v0.0.1")}
|
25
|
+
let(:v_0_0_2) {Releasetool::Version.new("v0.0.2")}
|
26
|
+
let(:v_0_0_3) {Releasetool::Version.new("v0.0.3")}
|
27
|
+
|
28
|
+
it "is next" do
|
29
|
+
expect(v_0_0_1.next_patch).to eq(v_0_0_2)
|
30
|
+
end
|
31
|
+
it "is next" do
|
32
|
+
expect(v_0_0_2.next_patch).to eq(v_0_0_3)
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
describe "next_minor" do
|
37
|
+
let(:v_0_0_1) {Releasetool::Version.new("v0.0.1")}
|
38
|
+
let(:v_0_1_0) {Releasetool::Version.new("v0.1.0")}
|
39
|
+
let(:v_0_2_0) {Releasetool::Version.new("v0.2.0")}
|
40
|
+
|
41
|
+
it "is next" do
|
42
|
+
expect(v_0_0_1.next_minor).to eq(v_0_1_0)
|
43
|
+
end
|
44
|
+
it "is next" do
|
45
|
+
expect(v_0_1_0.next_minor).to eq(v_0_2_0)
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
describe "next_major" do
|
50
|
+
let(:v_0_1_1) {Releasetool::Version.new("v0.1.1")}
|
51
|
+
let(:v_1_0_0) {Releasetool::Version.new("v1.0.0")}
|
52
|
+
let(:v_2_0_0) {Releasetool::Version.new("v2.0.0")}
|
53
|
+
|
54
|
+
it "is next" do
|
55
|
+
expect(v_0_1_1.next_major).to eq(v_1_0_0)
|
56
|
+
end
|
57
|
+
it "is next" do
|
58
|
+
expect(v_1_0_0.next_major).to eq(v_2_0_0)
|
59
|
+
end
|
60
|
+
end
|
61
|
+
|
62
|
+
describe "==" do
|
63
|
+
let(:v_0_0_2) {Releasetool::Version.new("v0.0.2")}
|
64
|
+
|
65
|
+
it "is self same" do
|
66
|
+
expect(v_0_0_2 == v_0_0_2).to be_truthy
|
67
|
+
end
|
68
|
+
it "is same if other is a version of same" do
|
69
|
+
expect(v_0_0_2 == Releasetool::Version.new("v0.0.2")).to be_truthy
|
70
|
+
end
|
71
|
+
it "is false if other is otherversion " do
|
72
|
+
expect(v_0_0_2 == Releasetool::Version.new("v0.0.3")).to be_falsey
|
73
|
+
end
|
74
|
+
end
|
75
|
+
end
|
metadata
ADDED
@@ -0,0 +1,128 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: releasetool
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.2.0
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- Tim Diggins
|
8
|
+
autorequire:
|
9
|
+
bindir: bin
|
10
|
+
cert_chain: []
|
11
|
+
date: 2020-05-05 00:00:00.000000000 Z
|
12
|
+
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: thor
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - "~>"
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: '0.18'
|
20
|
+
type: :runtime
|
21
|
+
prerelease: false
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
23
|
+
requirements:
|
24
|
+
- - "~>"
|
25
|
+
- !ruby/object:Gem::Version
|
26
|
+
version: '0.18'
|
27
|
+
- !ruby/object:Gem::Dependency
|
28
|
+
name: bundler
|
29
|
+
requirement: !ruby/object:Gem::Requirement
|
30
|
+
requirements:
|
31
|
+
- - "~>"
|
32
|
+
- !ruby/object:Gem::Version
|
33
|
+
version: '1.3'
|
34
|
+
type: :development
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: !ruby/object:Gem::Requirement
|
37
|
+
requirements:
|
38
|
+
- - "~>"
|
39
|
+
- !ruby/object:Gem::Version
|
40
|
+
version: '1.3'
|
41
|
+
- !ruby/object:Gem::Dependency
|
42
|
+
name: rake
|
43
|
+
requirement: !ruby/object:Gem::Requirement
|
44
|
+
requirements:
|
45
|
+
- - ">="
|
46
|
+
- !ruby/object:Gem::Version
|
47
|
+
version: '0'
|
48
|
+
type: :development
|
49
|
+
prerelease: false
|
50
|
+
version_requirements: !ruby/object:Gem::Requirement
|
51
|
+
requirements:
|
52
|
+
- - ">="
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: '0'
|
55
|
+
- !ruby/object:Gem::Dependency
|
56
|
+
name: rspec
|
57
|
+
requirement: !ruby/object:Gem::Requirement
|
58
|
+
requirements:
|
59
|
+
- - ">="
|
60
|
+
- !ruby/object:Gem::Version
|
61
|
+
version: '0'
|
62
|
+
type: :development
|
63
|
+
prerelease: false
|
64
|
+
version_requirements: !ruby/object:Gem::Requirement
|
65
|
+
requirements:
|
66
|
+
- - ">="
|
67
|
+
- !ruby/object:Gem::Version
|
68
|
+
version: '0'
|
69
|
+
description: Some release-related functions, initially just release notes management
|
70
|
+
and creation
|
71
|
+
email:
|
72
|
+
- tim@red56.co.uk
|
73
|
+
executables:
|
74
|
+
- release
|
75
|
+
extensions: []
|
76
|
+
extra_rdoc_files: []
|
77
|
+
files:
|
78
|
+
- ".gitignore"
|
79
|
+
- Gemfile
|
80
|
+
- LICENSE.txt
|
81
|
+
- README.md
|
82
|
+
- Rakefile
|
83
|
+
- bin/release
|
84
|
+
- lib/releasetool.rb
|
85
|
+
- lib/releasetool/release.rb
|
86
|
+
- lib/releasetool/util.rb
|
87
|
+
- lib/releasetool/version.rb
|
88
|
+
- lib/tasks/release_thor.rb
|
89
|
+
- release_notes/__TEMPLATE__.md
|
90
|
+
- release_notes/v0.0.1.md
|
91
|
+
- release_notes/v0.0.2.md
|
92
|
+
- release_notes/v0.0.3.md
|
93
|
+
- release_notes/v0.1.0.md
|
94
|
+
- release_notes/v0.1.1.md
|
95
|
+
- release_notes/v0.2.0.md
|
96
|
+
- releasetool.gemspec
|
97
|
+
- spec/fixtures/example_with_releases.tar
|
98
|
+
- spec/releasetool_spec.rb
|
99
|
+
- spec/spec_helper.rb
|
100
|
+
- spec/version_spec.rb
|
101
|
+
homepage: ''
|
102
|
+
licenses:
|
103
|
+
- MIT
|
104
|
+
metadata: {}
|
105
|
+
post_install_message:
|
106
|
+
rdoc_options: []
|
107
|
+
require_paths:
|
108
|
+
- lib
|
109
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
110
|
+
requirements:
|
111
|
+
- - ">="
|
112
|
+
- !ruby/object:Gem::Version
|
113
|
+
version: '0'
|
114
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
115
|
+
requirements:
|
116
|
+
- - ">="
|
117
|
+
- !ruby/object:Gem::Version
|
118
|
+
version: '0'
|
119
|
+
requirements: []
|
120
|
+
rubygems_version: 3.0.8
|
121
|
+
signing_key:
|
122
|
+
specification_version: 4
|
123
|
+
summary: Release management tools
|
124
|
+
test_files:
|
125
|
+
- spec/fixtures/example_with_releases.tar
|
126
|
+
- spec/releasetool_spec.rb
|
127
|
+
- spec/spec_helper.rb
|
128
|
+
- spec/version_spec.rb
|