scm_workspace 0.0.2 → 0.1.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/scm_workspace/version.rb +1 -1
- data/lib/scm_workspace.rb +53 -54
- data/scm_workspace.gemspec +1 -1
- data/spec/scm_workspace_spec.rb +67 -66
- metadata +6 -6
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: c387c99f98b27629fa7718d82dcfc15f586673ce
|
4
|
+
data.tar.gz: e81f9659b83c087db6413db421ea4b8cb1453e14
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 48b7feb1d23397737c314eabac700121d87ed9a0dead394edd8be41936107275876e01e7615ef7427963199571a012529feb07cf58b91cd8c0956a6f79a2036f
|
7
|
+
data.tar.gz: afd711128955f9c4361d90531a9b8ec6fa46768cb6a72d9da7a885254dd504db6e6a9c267c8ef288bdae65b345e3b490dc3383c206b0ba2463efbe4165dc2f9d
|
data/lib/scm_workspace.rb
CHANGED
@@ -12,9 +12,13 @@ class ScmWorkspace
|
|
12
12
|
|
13
13
|
attr_reader :root
|
14
14
|
attr_writer :logger
|
15
|
+
attr_accessor :svn_branch_prefix
|
16
|
+
attr_accessor :verbose
|
15
17
|
def initialize(config, options = {})
|
16
18
|
@root = config[:workspace]
|
17
19
|
@logger = options[:logger]
|
20
|
+
@verbose = options[:verbose] || (ENV["VERBOSE"] =~ /true|yes|on/)
|
21
|
+
@svn_branch_prefix = options[:svn_branch_prefix] || ENV["SVN_BRANCH_PREFIX"] || "branches"
|
18
22
|
end
|
19
23
|
|
20
24
|
def logger
|
@@ -23,17 +27,17 @@ class ScmWorkspace
|
|
23
27
|
|
24
28
|
def puts_info(msg)
|
25
29
|
logger.info(msg)
|
26
|
-
$stdout.puts(msg)
|
30
|
+
$stdout.puts(msg) if verbose
|
27
31
|
end
|
28
32
|
|
29
33
|
def configure(url)
|
30
|
-
|
31
|
-
|
34
|
+
if configured?
|
35
|
+
msg = "#{repo_dir} is not empty. You must clear it"
|
36
|
+
msg << "\nls -la #{repo_dir}" << `ls -la #{repo_dir}` if verbose
|
37
|
+
raise msg
|
38
|
+
end
|
32
39
|
url, opt = url.split(/\s+/, 2)
|
33
40
|
scm_type = self.class.guess_scm_type(url)
|
34
|
-
options = opt ? parse_options(opt, scm_type) : {}
|
35
|
-
options['url'] = url
|
36
|
-
save_options(options)
|
37
41
|
case scm_type
|
38
42
|
when :git then
|
39
43
|
logger.info("*" * 100)
|
@@ -43,7 +47,8 @@ class ScmWorkspace
|
|
43
47
|
@git = Git.clone(url, repo_dir)
|
44
48
|
when :svn then
|
45
49
|
Dir.chdir(@root) do
|
46
|
-
cmd = "git svn clone #{url} #{repo_dir} #{opt}
|
50
|
+
cmd = "git svn clone #{url} #{repo_dir} #{opt}"
|
51
|
+
cmd << " > /dev/null 2>&1" unless verbose
|
47
52
|
logger.info("*" * 100)
|
48
53
|
logger.info("SCM configure")
|
49
54
|
puts_info "cd #{@root} && " + cmd
|
@@ -56,8 +61,13 @@ class ScmWorkspace
|
|
56
61
|
end
|
57
62
|
|
58
63
|
def clear
|
59
|
-
|
60
|
-
|
64
|
+
return unless Dir.exist?(repo_dir)
|
65
|
+
Dir.chdir(repo_dir) do
|
66
|
+
(Dir.glob("*") + Dir.glob(".*")).each do |d|
|
67
|
+
next if d =~ /\A\.+\Z/
|
68
|
+
FileUtils.remove_entry_secure(d)
|
69
|
+
end
|
70
|
+
end
|
61
71
|
end
|
62
72
|
|
63
73
|
def checkout(branch_name)
|
@@ -169,20 +179,39 @@ class ScmWorkspace
|
|
169
179
|
def current_branch_name
|
170
180
|
return nil unless configured?
|
171
181
|
case scm_type
|
172
|
-
when :git then
|
173
|
-
|
174
|
-
|
175
|
-
|
176
|
-
|
177
|
-
|
178
|
-
|
179
|
-
|
180
|
-
|
181
|
-
|
182
|
-
|
183
|
-
|
184
|
-
|
182
|
+
when :git then git_current_branch_name
|
183
|
+
when :svn then svn_current_branch_name
|
184
|
+
end
|
185
|
+
end
|
186
|
+
|
187
|
+
def git_current_branch_name(dir = repo_dir)
|
188
|
+
return nil unless Dir.exist?(dir)
|
189
|
+
Dir.chdir(dir) do
|
190
|
+
# http://qiita.com/sugyan/items/83e060e895fa8ef2038c
|
191
|
+
result = `git symbolic-ref --short HEAD`.strip
|
192
|
+
return result unless result.nil? || result.empty?
|
193
|
+
result = `git status`.scan(/On branch\s*(.+)\s*$/).flatten.first
|
194
|
+
return result unless result.nil? || result.empty?
|
195
|
+
work = `git log --decorate -1`.scan(/^commit\s[0-9a-f]+\s\((.+)\)/).
|
196
|
+
flatten.first.split(/,/).map(&:strip).reject{|s| s =~ /HEAD\Z/}
|
197
|
+
r = work.select{|s| s =~ /origin\//}.first
|
198
|
+
r ||= work.first
|
199
|
+
result = r.sub(/\Aorigin\//, '')
|
200
|
+
return result
|
185
201
|
end
|
202
|
+
rescue => e
|
203
|
+
# puts "[#{e.class}] #{e.message}"
|
204
|
+
# puts "Dir.pwd: #{Dir.pwd}"
|
205
|
+
# puts "git status\n" << `git status`
|
206
|
+
raise e
|
207
|
+
end
|
208
|
+
|
209
|
+
def svn_current_branch_name
|
210
|
+
info = svn_info
|
211
|
+
r = info[:url].sub(info[:repository_root], '')
|
212
|
+
r.sub!(/\A\//, '')
|
213
|
+
r.sub!(svn_branch_prefix + "/", '')
|
214
|
+
r
|
186
215
|
end
|
187
216
|
|
188
217
|
def current_tag_names
|
@@ -193,15 +222,11 @@ class ScmWorkspace
|
|
193
222
|
|
194
223
|
|
195
224
|
def repo_dir
|
196
|
-
|
197
|
-
end
|
198
|
-
|
199
|
-
def options_path
|
200
|
-
File.join(@root, "options.yml")
|
225
|
+
@root
|
201
226
|
end
|
202
227
|
|
203
228
|
def configured?
|
204
|
-
Dir.exist?(repo_dir)
|
229
|
+
Dir.exist?(File.join(repo_dir, ".git"))
|
205
230
|
end
|
206
231
|
|
207
232
|
def cleared?
|
@@ -236,32 +261,6 @@ class ScmWorkspace
|
|
236
261
|
}
|
237
262
|
}
|
238
263
|
|
239
|
-
def parse_options(opt, scm_type)
|
240
|
-
# "-T trunk --branches branches --tags tags -hoge --on" という文字列を
|
241
|
-
# [["-T", "trunk"], ["--branches", "branches"], ["--tags", "tags"], ["-hoge", nil], ["--on", nil]]
|
242
|
-
# という風に分割します
|
243
|
-
key_values = opt.scan(/(-[^\s]+)(?:\=|\s+)?([^-][^\s]+)?/)
|
244
|
-
result = key_values.each_with_object({}){|(k,v), d| d[k.sub(/\A-{1,2}/, '').gsub(/-/, '_')] = v }
|
245
|
-
CONFIGURE_OPTIONS[scm_type].each do |short_key, long_key|
|
246
|
-
if v = result.delete(short_key)
|
247
|
-
result[long_key] = v
|
248
|
-
end
|
249
|
-
end
|
250
|
-
result
|
251
|
-
end
|
252
|
-
|
253
|
-
def save_options(hash)
|
254
|
-
open(options_path, "w") do |f|
|
255
|
-
YAML.dump(hash, f)
|
256
|
-
end
|
257
|
-
end
|
258
|
-
|
259
|
-
def load_options
|
260
|
-
return {} unless File.readable?(options_path)
|
261
|
-
YAML.load_file(options_path)
|
262
|
-
end
|
263
|
-
alias_method :options, :load_options
|
264
|
-
|
265
264
|
def git_repo?
|
266
265
|
return nil unless configured?
|
267
266
|
!git.remotes.empty? rescue false
|
data/scm_workspace.gemspec
CHANGED
@@ -23,7 +23,7 @@ Gem::Specification.new do |spec|
|
|
23
23
|
|
24
24
|
spec.add_development_dependency "bundler", "~> 1.3"
|
25
25
|
spec.add_development_dependency "rake"
|
26
|
-
spec.add_development_dependency "rspec"
|
26
|
+
spec.add_development_dependency "rspec"
|
27
27
|
|
28
28
|
spec.add_development_dependency "pry"
|
29
29
|
spec.add_development_dependency "fuubar"
|
data/spec/scm_workspace_spec.rb
CHANGED
@@ -7,27 +7,27 @@ require 'fileutils'
|
|
7
7
|
# ApiServerモードでもScmWorkspaceクラスを使用するので、参照だけはできることを確認する。
|
8
8
|
describe ScmWorkspace do
|
9
9
|
|
10
|
-
before(:all)
|
10
|
+
before(:all) do
|
11
|
+
@tmp_workspace = Dir.mktmpdir
|
12
|
+
@scm_workspace = ScmWorkspace.new(workspace: File.join(@tmp_workspace, "workspace"))
|
13
|
+
end
|
11
14
|
after(:all){ FileUtils.remove_entry_secure(@tmp_workspace) }
|
12
|
-
let(:tmp_workspace){ @tmp_workspace }
|
13
|
-
let(:scm_workspace){ ScmWorkspace.new(workspace: tmp_workspace) }
|
14
15
|
|
15
16
|
context "not depend on git" do
|
16
|
-
subject{ scm_workspace }
|
17
|
+
subject{ @scm_workspace }
|
17
18
|
its(:repo_dir){ should_not == nil }
|
18
|
-
its(:options_path){ should_not == nil }
|
19
19
|
it{ subject.configured? }
|
20
20
|
it{ subject.cleared? }
|
21
21
|
end
|
22
22
|
|
23
23
|
context "git", git: true do
|
24
|
-
|
24
|
+
before(:all){ @url = "git://github.com/akm/git_sandbox.git" }
|
25
25
|
|
26
26
|
context "before configuring" do
|
27
27
|
before do
|
28
|
-
|
28
|
+
@scm_workspace.clear
|
29
29
|
end
|
30
|
-
subject{ scm_workspace }
|
30
|
+
subject{ @scm_workspace }
|
31
31
|
|
32
32
|
its(:configured?){ should == false}
|
33
33
|
its(:scm_type){ should == nil}
|
@@ -48,15 +48,14 @@ describe ScmWorkspace do
|
|
48
48
|
|
49
49
|
context "after configuring" do
|
50
50
|
before(:all) do
|
51
|
-
|
52
|
-
scm_workspace.configure(url)
|
51
|
+
@scm_workspace.clear
|
52
|
+
@scm_workspace.configure(@url)
|
53
53
|
end
|
54
|
-
subject{ scm_workspace }
|
54
|
+
subject{ @scm_workspace }
|
55
55
|
|
56
|
-
its(:options){ should == {"url" => url} }
|
57
56
|
its(:configured?){ should == true}
|
58
57
|
its(:cleared?){ should == false }
|
59
|
-
its(:url){ should == url }
|
58
|
+
its(:url){ should == @url }
|
60
59
|
|
61
60
|
its(:scm_type){ should == :git}
|
62
61
|
its(:git_repo?){ should == true }
|
@@ -71,13 +70,13 @@ describe ScmWorkspace do
|
|
71
70
|
its(:current_commit_key){ should == "a0eaf8cca31080ca26edbae0daddaa9931edd6d6" }
|
72
71
|
|
73
72
|
it :fetch do
|
74
|
-
scm_workspace.fetch
|
73
|
+
@scm_workspace.fetch
|
75
74
|
end
|
76
75
|
|
77
76
|
context "duplicated configuration" do
|
78
77
|
it do
|
79
78
|
expect{
|
80
|
-
scm_workspace.configure(url)
|
79
|
+
@scm_workspace.configure(@url)
|
81
80
|
}.to raise_error(/not empty/i)
|
82
81
|
end
|
83
82
|
end
|
@@ -86,28 +85,28 @@ describe ScmWorkspace do
|
|
86
85
|
describe :checkout do
|
87
86
|
context "another branch" do
|
88
87
|
before(:all) do
|
89
|
-
|
90
|
-
scm_workspace.configure(url)
|
91
|
-
scm_workspace.checkout("0.1")
|
88
|
+
@scm_workspace.clear
|
89
|
+
@scm_workspace.configure(@url)
|
90
|
+
@scm_workspace.checkout("0.1")
|
92
91
|
end
|
93
|
-
subject{ scm_workspace }
|
92
|
+
subject{ @scm_workspace }
|
94
93
|
its(:current_branch_name){ should == "0.1" }
|
95
94
|
its(:current_tag_names){ should =~ %w[v0.1.0] }
|
96
95
|
end
|
97
96
|
|
98
97
|
context "branch is updated" do
|
99
98
|
before(:all) do
|
100
|
-
|
101
|
-
scm_workspace.configure(url)
|
102
|
-
Dir.chdir(scm_workspace.repo_dir) do
|
99
|
+
@scm_workspace.clear
|
100
|
+
@scm_workspace.configure(@url)
|
101
|
+
Dir.chdir(@scm_workspace.repo_dir) do
|
103
102
|
# バージョンを巻き戻す
|
104
103
|
system("git reset --hard a68a53610407e6ba30939326af743d3b734bb53d")
|
105
104
|
end
|
106
105
|
end
|
107
106
|
it "checkout again" do
|
108
|
-
scm_workspace.status.should =~ /7 commits/
|
109
|
-
scm_workspace.checkout("develop")
|
110
|
-
scm_workspace.status.should =~ /up-to-dated/
|
107
|
+
@scm_workspace.status.should =~ /7 commits/
|
108
|
+
@scm_workspace.checkout("develop")
|
109
|
+
@scm_workspace.status.should =~ /up-to-dated/
|
111
110
|
end
|
112
111
|
end
|
113
112
|
end
|
@@ -116,24 +115,24 @@ describe ScmWorkspace do
|
|
116
115
|
%w[v0.0.1 v0.0.2 v0.1.0].each do |tag|
|
117
116
|
context "#{tag} in develop" do
|
118
117
|
before(:all) do
|
119
|
-
|
120
|
-
scm_workspace.configure(url)
|
121
|
-
scm_workspace.checkout("develop")
|
122
|
-
scm_workspace.move(tag)
|
118
|
+
@scm_workspace.clear
|
119
|
+
@scm_workspace.configure(@url)
|
120
|
+
@scm_workspace.checkout("develop")
|
121
|
+
@scm_workspace.move(tag)
|
123
122
|
end
|
124
|
-
subject{ scm_workspace }
|
123
|
+
subject{ @scm_workspace }
|
125
124
|
its(:current_branch_name){ should == "develop" }
|
126
125
|
its(:current_tag_names){ should =~ [tag] }
|
127
126
|
end
|
128
127
|
end
|
129
128
|
context "reset to fix wrong reset" do
|
130
129
|
before(:all) do
|
131
|
-
|
132
|
-
scm_workspace.configure(url)
|
133
|
-
scm_workspace.checkout("develop")
|
134
|
-
scm_workspace.move("v0.1.0")
|
130
|
+
@scm_workspace.clear
|
131
|
+
@scm_workspace.configure(@url)
|
132
|
+
@scm_workspace.checkout("develop")
|
133
|
+
@scm_workspace.move("v0.1.0")
|
135
134
|
end
|
136
|
-
subject{ scm_workspace }
|
135
|
+
subject{ @scm_workspace }
|
137
136
|
it do
|
138
137
|
subject.current_branch_name.should == "develop"
|
139
138
|
subject.current_tag_names.should =~ ["v0.1.0"]
|
@@ -146,35 +145,37 @@ describe ScmWorkspace do
|
|
146
145
|
|
147
146
|
describe :clear do
|
148
147
|
before(:all) do
|
149
|
-
|
150
|
-
scm_workspace.configure(url)
|
148
|
+
@scm_workspace.clear
|
149
|
+
@scm_workspace.configure(@url)
|
151
150
|
end
|
152
151
|
|
153
152
|
it do
|
154
|
-
scm_workspace.cleared?.should == false
|
155
|
-
scm_workspace.clear
|
156
|
-
scm_workspace.cleared?.should == true
|
157
|
-
Dir.exist?(scm_workspace.repo_dir).should ==
|
153
|
+
@scm_workspace.cleared?.should == false
|
154
|
+
@scm_workspace.clear
|
155
|
+
@scm_workspace.cleared?.should == true
|
156
|
+
Dir.exist?(@scm_workspace.repo_dir).should == true
|
157
|
+
Dir.exist?(File.join(@scm_workspace.repo_dir, ".git")).should == false
|
158
158
|
end
|
159
159
|
end
|
160
160
|
|
161
161
|
end
|
162
162
|
|
163
163
|
context "svn", svn: true do
|
164
|
-
|
165
|
-
|
164
|
+
before(:all) do
|
165
|
+
@base_url = "http://rubeus.googlecode.com/svn"
|
166
|
+
@cloning_url = "#{@base_url} -T trunk --branches branches --tags tags"
|
167
|
+
end
|
166
168
|
|
167
169
|
context "after configuring" do
|
168
170
|
before(:all) do
|
169
|
-
|
170
|
-
scm_workspace.configure(cloning_url)
|
171
|
+
@scm_workspace.clear
|
172
|
+
@scm_workspace.configure(@cloning_url)
|
171
173
|
end
|
172
|
-
subject{ scm_workspace }
|
174
|
+
subject{ @scm_workspace }
|
173
175
|
|
174
176
|
its(:configured?){ should == true}
|
175
177
|
its(:cleared?){ should == false }
|
176
|
-
its(:url){ should == base_url }
|
177
|
-
its(:options){ should == {"url" => base_url, "trunk" => "trunk", "branches" => "branches", "tags" => "tags"} }
|
178
|
+
its(:url){ should == @base_url }
|
178
179
|
|
179
180
|
its(:scm_type){ should == :svn}
|
180
181
|
its(:git_repo?){ should == false }
|
@@ -190,20 +191,20 @@ describe ScmWorkspace do
|
|
190
191
|
its(:current_commit_key){ should =~ /\A[0-9a-f]{40}:247\Z/ }
|
191
192
|
|
192
193
|
it :fetch do
|
193
|
-
scm_workspace.fetch
|
194
|
+
@scm_workspace.fetch
|
194
195
|
end
|
195
196
|
end
|
196
197
|
|
197
198
|
context "duplicated configuration" do
|
198
199
|
before(:all) do
|
199
|
-
|
200
|
-
scm_workspace.configure(cloning_url)
|
200
|
+
@scm_workspace.clear
|
201
|
+
@scm_workspace.configure(@cloning_url)
|
201
202
|
end
|
202
|
-
subject{ scm_workspace }
|
203
|
+
subject{ @scm_workspace }
|
203
204
|
|
204
205
|
it do
|
205
206
|
expect{
|
206
|
-
scm_workspace.configure(cloning_url)
|
207
|
+
@scm_workspace.configure(@cloning_url)
|
207
208
|
}.to raise_error(/not empty/i)
|
208
209
|
end
|
209
210
|
end
|
@@ -213,11 +214,11 @@ describe ScmWorkspace do
|
|
213
214
|
|
214
215
|
context branch_name do
|
215
216
|
before(:all) do
|
216
|
-
|
217
|
-
scm_workspace.configure(cloning_url)
|
218
|
-
scm_workspace.checkout(branch_name)
|
217
|
+
@scm_workspace.clear
|
218
|
+
@scm_workspace.configure(@cloning_url)
|
219
|
+
@scm_workspace.checkout(branch_name)
|
219
220
|
end
|
220
|
-
subject{ scm_workspace }
|
221
|
+
subject{ @scm_workspace }
|
221
222
|
its(:current_branch_name){ should == branch_name }
|
222
223
|
its(:current_tag_names){ should == [] }
|
223
224
|
end
|
@@ -226,21 +227,21 @@ describe ScmWorkspace do
|
|
226
227
|
|
227
228
|
context "branch is updated" do
|
228
229
|
before(:all) do
|
229
|
-
|
230
|
-
scm_workspace.configure(cloning_url)
|
231
|
-
scm_workspace.checkout("trunk")
|
232
|
-
Dir.chdir(scm_workspace.repo_dir) do
|
230
|
+
@scm_workspace.clear
|
231
|
+
@scm_workspace.configure(@cloning_url)
|
232
|
+
@scm_workspace.checkout("trunk")
|
233
|
+
Dir.chdir(@scm_workspace.repo_dir) do
|
233
234
|
# バージョンを巻き戻す
|
234
235
|
system("git reset --hard HEAD~3")
|
235
236
|
end
|
236
237
|
end
|
237
238
|
|
238
239
|
it "checkout again" do
|
239
|
-
scm_workspace.current_commit_key.should =~ /\A[0-9a-f]{40}:244\Z/
|
240
|
-
scm_workspace.status.should =~ /3 commits.*current revision: 244.*latest revision: 247/
|
241
|
-
scm_workspace.checkout("trunk")
|
242
|
-
scm_workspace.current_commit_key.should =~ /\A[0-9a-f]{40}:247\Z/
|
243
|
-
scm_workspace.status.should =~ /up-to-dated/
|
240
|
+
@scm_workspace.current_commit_key.should =~ /\A[0-9a-f]{40}:244\Z/
|
241
|
+
@scm_workspace.status.should =~ /3 commits.*current revision: 244.*latest revision: 247/
|
242
|
+
@scm_workspace.checkout("trunk")
|
243
|
+
@scm_workspace.current_commit_key.should =~ /\A[0-9a-f]{40}:247\Z/
|
244
|
+
@scm_workspace.status.should =~ /up-to-dated/
|
244
245
|
end
|
245
246
|
|
246
247
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: scm_workspace
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0
|
4
|
+
version: 0.1.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- akima
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2013-10-
|
11
|
+
date: 2013-10-07 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: git
|
@@ -70,16 +70,16 @@ dependencies:
|
|
70
70
|
name: rspec
|
71
71
|
requirement: !ruby/object:Gem::Requirement
|
72
72
|
requirements:
|
73
|
-
- -
|
73
|
+
- - '>='
|
74
74
|
- !ruby/object:Gem::Version
|
75
|
-
version:
|
75
|
+
version: '0'
|
76
76
|
type: :development
|
77
77
|
prerelease: false
|
78
78
|
version_requirements: !ruby/object:Gem::Requirement
|
79
79
|
requirements:
|
80
|
-
- -
|
80
|
+
- - '>='
|
81
81
|
- !ruby/object:Gem::Version
|
82
|
-
version:
|
82
|
+
version: '0'
|
83
83
|
- !ruby/object:Gem::Dependency
|
84
84
|
name: pry
|
85
85
|
requirement: !ruby/object:Gem::Requirement
|