tmp-repo 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 750d50105e4fe0fd086ed4c10c8bf3f4648b17c6
4
+ data.tar.gz: ebacae5e6fd5562a16c78ee84f1f262d45546620
5
+ SHA512:
6
+ metadata.gz: d57090af6e6155920bea50f1d8fd2513bcae60ec2030c9eb5bead81e0c2f9ff740e5165c27b244edf097a130ddf8ca1bd178f0c68e37dfbd93138a72a82ef943
7
+ data.tar.gz: ab3f893e67603d9a024f8bf18c44a042e82b2bd56a68771684daa7c793efb50233c7ed527524ac53906796c91d08b097e2c1b84ef818fd001f36e355bac60833
data/Gemfile ADDED
@@ -0,0 +1,13 @@
1
+ source "https://rubygems.org"
2
+
3
+ gemspec
4
+
5
+ group :development, :test do
6
+ gem 'pry-nav'
7
+ gem 'rake'
8
+ end
9
+
10
+ group :test do
11
+ gem 'rspec'
12
+ gem 'rr'
13
+ end
@@ -0,0 +1,3 @@
1
+ == 1.0.0
2
+
3
+ * Birthday!
@@ -0,0 +1,120 @@
1
+ tmp-repo
2
+ ========
3
+
4
+ [![Build Status](https://travis-ci.org/camertron/tmp-repo.svg?branch=master)](http://travis-ci.org/camertron/tmp-repo)
5
+
6
+ Creates and manages git repositories in the operating system's temporary directory. It does this by providing a thin wrapper around the git binary that's pointed at a randomly generated temporary folder.
7
+
8
+ ## Installation
9
+
10
+ `gem install tmp-repo`
11
+
12
+ ## Usage
13
+
14
+ ```ruby
15
+ require 'tmp-repo'
16
+ ```
17
+
18
+ ### Basics
19
+
20
+ Creating a new `TmpRepo` will automatically create a randomly named folder in your system's temp directory and initialize a git repository in it:
21
+
22
+ ```ruby
23
+ repo = TmpRepo.new
24
+ repo.working_dir # => #<Pathname:/var/folders/3x/n10r69b16bq_rlcqr3fy0rwc0000gn/T/b068487773901ffe23e66a8259711fa1>
25
+ ```
26
+
27
+ Once created, you can ask your `TmpRepo` questions and perform operations on it. Don't forget to clean up after yourself when you're finished:
28
+
29
+ ```ruby
30
+ repo.unlink
31
+ ```
32
+
33
+ ### Creating Files
34
+
35
+ ```ruby
36
+ repo.create_file('foo.txt') do |f|
37
+ f.write("I'm a new file!")
38
+ end
39
+ ```
40
+
41
+ OR
42
+
43
+ ```ruby
44
+ file = repo.create_file('foo.txt')
45
+ file.write("I'm a new file!")
46
+ file.close
47
+ ```
48
+
49
+ ### Branching
50
+
51
+ To create a new branch:
52
+
53
+ ```ruby
54
+ repo.create_branch('my_new_branch')
55
+ ```
56
+
57
+ To check out a branch:
58
+
59
+ ```ruby
60
+ repo.checkout('my_other_branch')
61
+ ```
62
+
63
+ To get the current branch:
64
+
65
+ ```ruby
66
+ repo.current_branch # => 'master'
67
+ ```
68
+
69
+ ### Staging and Committing
70
+
71
+ To add all files to the git stage:
72
+
73
+ ```ruby
74
+ repo.add_all
75
+ ```
76
+
77
+ To commit staged files:
78
+
79
+ ```ruby
80
+ repo.commit('Commit message')
81
+ ```
82
+
83
+ ### Repo Status
84
+
85
+ `TmpRepo` instances provide a convenient way to retrieve the status of the repository via the `status` method. `status` return values are a simple hash of arrays:
86
+
87
+ ```ruby
88
+ status = repo.status
89
+ status[:new_file] # => ['file1.txt', 'file2.txt']
90
+ status[:deleted] # => ['file3.txt']
91
+ status[:modified] # => ['file4.txt']
92
+ ```
93
+
94
+ ### Custom Commands
95
+
96
+ This library only provides wrapper methods around the most common git commands. To run additional git commands, use the `git` method:
97
+
98
+ ```ruby
99
+ repo.git('rebase master')
100
+ ```
101
+
102
+ In addition, the lower-level `in_repo` method wraps the given block in a `Dir.chdir`, meaning the block is executed in the context of the repo's working directory:
103
+
104
+ ```ruby
105
+ repo.in_repo do
106
+ `ls` # list files in the repo's working directory
107
+ end
108
+ ```
109
+
110
+ ## Requirements
111
+
112
+ No external requirements.
113
+
114
+ ## Running Tests
115
+
116
+ `bundle exec rake` should do the trick.
117
+
118
+ ## Authors
119
+
120
+ * Cameron C. Dutro: http://github.com/camertron
@@ -0,0 +1,18 @@
1
+ # encoding: UTF-8
2
+
3
+ require 'rubygems' unless ENV['NO_RUBYGEMS']
4
+
5
+ require 'bundler'
6
+ require 'rspec/core/rake_task'
7
+ require 'rubygems/package_task'
8
+
9
+ require './lib/tmp-repo'
10
+
11
+ Bundler::GemHelper.install_tasks
12
+
13
+ task :default => :spec
14
+
15
+ desc 'Run specs'
16
+ RSpec::Core::RakeTask.new do |t|
17
+ t.pattern = './spec/**/*_spec.rb'
18
+ end
@@ -0,0 +1,117 @@
1
+ # encoding: UTF-8
2
+
3
+ require 'tmpdir'
4
+ require 'pathname'
5
+ require 'fileutils'
6
+ require 'securerandom'
7
+
8
+ class TmpRepo
9
+ class GitError < StandardError; end
10
+
11
+ attr_reader :working_dir
12
+
13
+ def initialize
14
+ @working_dir = Pathname(
15
+ File.join(Dir.tmpdir, SecureRandom.hex(16))
16
+ )
17
+
18
+ FileUtils.mkdir_p(working_dir)
19
+ git('init')
20
+ end
21
+
22
+ def unlink
23
+ FileUtils.rm_rf(working_dir.to_s)
24
+ nil
25
+ end
26
+
27
+ def create_file(new_file)
28
+ new_path = working_dir.join(new_file).to_s
29
+ handle = File.open(new_path, 'w+')
30
+
31
+ if block_given?
32
+ yield handle
33
+ handle.close
34
+ else
35
+ handle
36
+ end
37
+ end
38
+
39
+ def add_all
40
+ git('add -A')
41
+ end
42
+
43
+ def commit(message)
44
+ git("commit -m '#{message.gsub("'", "\\\\'")}'")
45
+ end
46
+
47
+ def checkout(ref)
48
+ git("checkout #{ref}")
49
+ end
50
+
51
+ def create_branch(branch_name)
52
+ git("checkout -b #{branch_name}")
53
+ end
54
+
55
+ def current_branch
56
+ git('rev-parse --abbrev-ref HEAD').strip
57
+ end
58
+
59
+ def status
60
+ parse_status(git('status'))
61
+ end
62
+
63
+ def git(command)
64
+ in_repo do
65
+ output = `git #{command}`
66
+
67
+ if $?.exitstatus != 0
68
+ raise GitError, output
69
+ end
70
+
71
+ output
72
+ end
73
+ end
74
+
75
+ def in_repo
76
+ Dir.chdir(working_dir.to_s) do
77
+ yield
78
+ end
79
+ end
80
+
81
+ private
82
+
83
+ def parse_status(status_text)
84
+ lines = status_text.split("\n")
85
+ status_hash = create_status_hash
86
+ statuses = possible_statuses_from(status_hash)
87
+
88
+ lines.each do |line|
89
+ index = -1
90
+
91
+ status = statuses.find do |status|
92
+ index = line =~ /#{Regexp.escape(status)}: /
93
+ end
94
+
95
+ if status
96
+ status = status_to_hash_key(status)
97
+ status_hash[status] << line[(index + status.size + 2)..-1].strip
98
+ end
99
+ end
100
+
101
+ status_hash
102
+ end
103
+
104
+ def status_to_hash_key(status)
105
+ status.gsub(' ', '_').to_sym
106
+ end
107
+
108
+ def possible_statuses_from(status_hash)
109
+ status_hash.keys.map do |status|
110
+ status.to_s.gsub('_', ' ').downcase
111
+ end
112
+ end
113
+
114
+ def create_status_hash
115
+ { modified: [], deleted: [], new_file: [] }
116
+ end
117
+ end
@@ -0,0 +1,5 @@
1
+ # encoding: UTF-8
2
+
3
+ class TmpRepo
4
+ VERSION = '1.0.0'
5
+ end
@@ -0,0 +1,9 @@
1
+ # encoding: UTF-8
2
+
3
+ require 'rspec'
4
+ require 'tmp-repo'
5
+ require 'pry-nav'
6
+
7
+ RSpec.configure do |config|
8
+ config.mock_with :rr
9
+ end
@@ -0,0 +1,183 @@
1
+ # encoding: UTF-8
2
+
3
+ require 'spec_helper'
4
+
5
+ describe TmpRepo do
6
+ let(:repo) do
7
+ TmpRepo.new
8
+ end
9
+
10
+ before(:each) do
11
+ repo.git('config user.email tester@tester.com')
12
+ repo.git('config user.name Tester McTesterson')
13
+ end
14
+
15
+ after(:each) do
16
+ repo.unlink
17
+ end
18
+
19
+ def in_repo
20
+ Dir.chdir(repo.working_dir.to_s) do
21
+ yield
22
+ end
23
+ end
24
+
25
+ describe '#initialize' do
26
+ it 'should initialize the repository' do
27
+ expect(repo.working_dir.join('.git')).to exist
28
+ end
29
+ end
30
+
31
+ describe '#unlink' do
32
+ it 'should delete the temp directory' do
33
+ repo.unlink
34
+ expect(repo.working_dir).to_not exist
35
+ end
36
+ end
37
+
38
+ describe '#create_file' do
39
+ it 'yields a file handle if given a block' do
40
+ repo.create_file('foo.txt') do |f|
41
+ expect(f).to be_a(IO)
42
+ f.write('foobar')
43
+ end
44
+
45
+ contents = File.read(repo.working_dir.join('foo.txt').to_s)
46
+ expect(contents).to eq('foobar')
47
+ end
48
+
49
+ it 'returns a file handle if not given a block' do
50
+ handle = repo.create_file('foo.txt')
51
+ expect(handle).to be_a(IO)
52
+ handle.write('foobarbaz')
53
+ handle.close
54
+
55
+ contents = File.read(repo.working_dir.join('foo.txt').to_s)
56
+ expect(contents).to eq('foobarbaz')
57
+ end
58
+ end
59
+
60
+ describe '#add_all' do
61
+ it 'stages all files' do
62
+ repo.create_file('foo.txt') { |f| f.write('foobar') }
63
+ repo.add_all
64
+
65
+ in_repo do
66
+ expect(`git status`).to match(/new file:[\s]+foo\.txt/)
67
+ end
68
+ end
69
+ end
70
+
71
+ describe '#commit' do
72
+ it 'commits the stage' do
73
+ repo.create_file('foo.txt') { |f| f.write('foobar') }
74
+ repo.add_all
75
+ repo.commit('Committing foobar')
76
+
77
+ in_repo do
78
+ expect(`git log`).to match(/Committing foobar/)
79
+ expect(`git show --name-only HEAD`).to include('foo.txt')
80
+ end
81
+ end
82
+ end
83
+
84
+ context 'with a single commit' do
85
+ before(:each) do
86
+ repo.create_file('foo.txt') do |f|
87
+ f.write('foobar')
88
+ end
89
+
90
+ repo.add_all
91
+ repo.commit('Foobar committed')
92
+ end
93
+
94
+ describe '#checkout' do
95
+ it 'checks out the given branch' do
96
+ in_repo do
97
+ `git checkout -b my_branch && git checkout master`
98
+ expect(`git rev-parse --abbrev-ref HEAD`.strip).to eq('master')
99
+ end
100
+
101
+ repo.checkout('my_branch')
102
+
103
+ in_repo do
104
+ expect(`git rev-parse --abbrev-ref HEAD`.strip).to eq('my_branch')
105
+ end
106
+ end
107
+ end
108
+
109
+ describe '#create_branch' do
110
+ it 'creates a new branch' do
111
+ repo.create_branch('new_branch')
112
+
113
+ in_repo do
114
+ expect(`git branch`).to include('new_branch')
115
+ end
116
+ end
117
+ end
118
+
119
+ describe '#current_branch' do
120
+ it 'returns the current branch name' do
121
+ in_repo { `git checkout -b cool_branch` }
122
+ expect(repo.current_branch).to eq('cool_branch')
123
+ end
124
+ end
125
+
126
+ describe '#status' do
127
+ it 'returns no results when there are no uncommitted changes' do
128
+ repo.status.tap do |status|
129
+ expect(status[:new_file]).to be_empty
130
+ expect(status[:modified]).to be_empty
131
+ expect(status[:deleted]).to be_empty
132
+ end
133
+ end
134
+
135
+ it 'shows new files' do
136
+ repo.create_file('hello.txt') do |f|
137
+ f.write('blarg blegh')
138
+ end
139
+
140
+ repo.add_all
141
+
142
+ repo.status.tap do |status|
143
+ expect(status[:new_file]).to include('hello.txt')
144
+ end
145
+ end
146
+
147
+ it 'shows modified files' do
148
+ in_repo do
149
+ File.open('foo.txt', 'w+') do |f|
150
+ f.write("\nI'm a change!")
151
+ end
152
+
153
+ repo.add_all
154
+
155
+ repo.status.tap do |status|
156
+ expect(status[:modified]).to include('foo.txt')
157
+ end
158
+ end
159
+ end
160
+
161
+ it 'shows deleted files' do
162
+ in_repo do
163
+ File.unlink('foo.txt')
164
+ repo.add_all
165
+
166
+ repo.status.tap do |status|
167
+ expect(status[:deleted]).to include('foo.txt')
168
+ end
169
+ end
170
+ end
171
+ end
172
+
173
+ describe '#git' do
174
+ it 'facilitates executing custom git commands and returning their output' do
175
+ expect(repo.git('branch')).to include('master')
176
+ end
177
+
178
+ it 'raises an error if the command fails' do
179
+ expect(lambda { repo.git('') }).to raise_error(TmpRepo::GitError)
180
+ end
181
+ end
182
+ end
183
+ end
@@ -0,0 +1,18 @@
1
+ $:.unshift File.join(File.dirname(__FILE__), 'lib')
2
+ require 'tmp-repo/version'
3
+
4
+ Gem::Specification.new do |s|
5
+ s.name = "tmp-repo"
6
+ s.version = ::TmpRepo::VERSION
7
+ s.authors = ["Cameron Dutro"]
8
+ s.email = ["camertron@gmail.com"]
9
+ s.homepage = "http://github.com/camertron"
10
+
11
+ s.description = s.summary = "Creates and manages a git repository in the operating system's temporary directory. Useful for running git operations in tests."
12
+
13
+ s.platform = Gem::Platform::RUBY
14
+ s.has_rdoc = true
15
+
16
+ s.require_path = 'lib'
17
+ s.files = Dir["{lib,spec}/**/*", "Gemfile", "History.txt", "README.md", "Rakefile", "tmp-repo.gemspec"]
18
+ end
metadata ADDED
@@ -0,0 +1,61 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: tmp-repo
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.0.0
5
+ platform: ruby
6
+ authors:
7
+ - Cameron Dutro
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+
12
+ date: 2014-08-21 00:00:00 Z
13
+ dependencies: []
14
+
15
+ description: Creates and manages a git repository in the operating system's temporary directory. Useful for running git operations in tests.
16
+ email:
17
+ - camertron@gmail.com
18
+ executables: []
19
+
20
+ extensions: []
21
+
22
+ extra_rdoc_files: []
23
+
24
+ files:
25
+ - Gemfile
26
+ - History.txt
27
+ - README.md
28
+ - Rakefile
29
+ - lib/tmp-repo.rb
30
+ - lib/tmp-repo/version.rb
31
+ - spec/spec_helper.rb
32
+ - spec/tmp-repo_spec.rb
33
+ - tmp-repo.gemspec
34
+ homepage: http://github.com/camertron
35
+ licenses: []
36
+
37
+ metadata: {}
38
+
39
+ post_install_message:
40
+ rdoc_options: []
41
+
42
+ require_paths:
43
+ - lib
44
+ required_ruby_version: !ruby/object:Gem::Requirement
45
+ requirements:
46
+ - &id001
47
+ - ">="
48
+ - !ruby/object:Gem::Version
49
+ version: "0"
50
+ required_rubygems_version: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - *id001
53
+ requirements: []
54
+
55
+ rubyforge_project:
56
+ rubygems_version: 2.2.2
57
+ signing_key:
58
+ specification_version: 4
59
+ summary: Creates and manages a git repository in the operating system's temporary directory. Useful for running git operations in tests.
60
+ test_files: []
61
+