dump 1.0.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.
- data/.autotest +13 -0
- data/.gitignore +12 -0
- data/LICENSE.txt +20 -0
- data/README.markdown +250 -0
- data/dump.gemspec +22 -0
- data/lib/dump.rb +3 -0
- data/lib/dump/capistrano.rb +1 -0
- data/lib/dump/railtie.rb +8 -0
- data/lib/dump_rake.rb +85 -0
- data/lib/dump_rake/archive_tar_minitar_fix.rb +8 -0
- data/lib/dump_rake/assets.rb +22 -0
- data/lib/dump_rake/continious_timeout.rb +38 -0
- data/lib/dump_rake/dump.rb +175 -0
- data/lib/dump_rake/dump_reader.rb +289 -0
- data/lib/dump_rake/dump_writer.rb +119 -0
- data/lib/dump_rake/env.rb +139 -0
- data/lib/dump_rake/env/filter.rb +26 -0
- data/lib/dump_rake/rails_root.rb +12 -0
- data/lib/dump_rake/table_manipulation.rb +131 -0
- data/lib/generators/assets_config/assets_config_generator.rb +16 -0
- data/lib/generators/assets_config/templates/assets +8 -0
- data/lib/tasks/assets.rake +17 -0
- data/lib/tasks/dump.rake +27 -0
- data/recipes/dump.rb +343 -0
- data/script/update_readme +21 -0
- data/spec/.gitignore +1 -0
- data/spec/.tmignore +1 -0
- data/spec/cycle_spec.rb +229 -0
- data/spec/db/database.example.yml +19 -0
- data/spec/db/schema.rb +7 -0
- data/spec/dummy-3.1.3/.gitignore +15 -0
- data/spec/dummy-3.1.3/.rspec +1 -0
- data/spec/dummy-3.1.3/Gemfile +23 -0
- data/spec/dummy-3.1.3/Gemfile.lock +159 -0
- data/spec/dummy-3.1.3/README +261 -0
- data/spec/dummy-3.1.3/Rakefile +7 -0
- data/spec/dummy-3.1.3/app/assets/images/rails.png +0 -0
- data/spec/dummy-3.1.3/app/assets/javascripts/application.js +9 -0
- data/spec/dummy-3.1.3/app/assets/stylesheets/application.css +7 -0
- data/spec/dummy-3.1.3/app/controllers/application_controller.rb +3 -0
- data/spec/dummy-3.1.3/app/helpers/application_helper.rb +2 -0
- data/spec/dummy-3.1.3/app/mailers/.gitkeep +0 -0
- data/spec/dummy-3.1.3/app/models/.gitkeep +0 -0
- data/spec/dummy-3.1.3/app/views/layouts/application.html.erb +14 -0
- data/spec/dummy-3.1.3/config.ru +4 -0
- data/spec/dummy-3.1.3/config/application.rb +54 -0
- data/spec/dummy-3.1.3/config/boot.rb +6 -0
- data/spec/dummy-3.1.3/config/database.yml +25 -0
- data/spec/dummy-3.1.3/config/environment.rb +5 -0
- data/spec/dummy-3.1.3/config/environments/development.rb +30 -0
- data/spec/dummy-3.1.3/config/environments/production.rb +60 -0
- data/spec/dummy-3.1.3/config/environments/test.rb +39 -0
- data/spec/dummy-3.1.3/config/initializers/backtrace_silencers.rb +7 -0
- data/spec/dummy-3.1.3/config/initializers/inflections.rb +10 -0
- data/spec/dummy-3.1.3/config/initializers/mime_types.rb +5 -0
- data/spec/dummy-3.1.3/config/initializers/secret_token.rb +7 -0
- data/spec/dummy-3.1.3/config/initializers/session_store.rb +8 -0
- data/spec/dummy-3.1.3/config/initializers/wrap_parameters.rb +14 -0
- data/spec/dummy-3.1.3/config/locales/en.yml +5 -0
- data/spec/dummy-3.1.3/config/routes.rb +58 -0
- data/spec/dummy-3.1.3/db/seeds.rb +7 -0
- data/spec/dummy-3.1.3/doc/README_FOR_APP +2 -0
- data/spec/dummy-3.1.3/lib/assets/.gitkeep +0 -0
- data/spec/dummy-3.1.3/lib/tasks/.gitkeep +0 -0
- data/spec/dummy-3.1.3/log/.gitkeep +0 -0
- data/spec/dummy-3.1.3/public/404.html +26 -0
- data/spec/dummy-3.1.3/public/422.html +26 -0
- data/spec/dummy-3.1.3/public/500.html +26 -0
- data/spec/dummy-3.1.3/public/favicon.ico +0 -0
- data/spec/dummy-3.1.3/public/index.html +241 -0
- data/spec/dummy-3.1.3/public/robots.txt +5 -0
- data/spec/dummy-3.1.3/script/rails +6 -0
- data/spec/dummy-3.1.3/spec/spec_helper.rb +32 -0
- data/spec/dummy-3.1.3/vendor/assets/stylesheets/.gitkeep +0 -0
- data/spec/dummy-3.1.3/vendor/plugins/.gitkeep +0 -0
- data/spec/lib/dump_rake/dump_reader_spec.rb +638 -0
- data/spec/lib/dump_rake/dump_spec.rb +291 -0
- data/spec/lib/dump_rake/dump_writer_spec.rb +328 -0
- data/spec/lib/dump_rake/env/filter_spec.rb +56 -0
- data/spec/lib/dump_rake/env_spec.rb +139 -0
- data/spec/lib/dump_rake/rails_root_spec.rb +45 -0
- data/spec/lib/dump_rake/table_manipulation_spec.rb +256 -0
- data/spec/lib/dump_rake_spec.rb +326 -0
- data/spec/recipes/dump_spec.rb +553 -0
- data/spec/spec.opts +4 -0
- data/spec/spec_helper.rb +34 -0
- data/spec/tasks/assets_spec.rb +92 -0
- data/spec/tasks/dump_spec.rb +107 -0
- metadata +272 -0
|
@@ -0,0 +1,291 @@
|
|
|
1
|
+
require File.dirname(__FILE__) + '/../../spec_helper'
|
|
2
|
+
|
|
3
|
+
describe DumpRake::Dump do
|
|
4
|
+
def dump_path(file_name)
|
|
5
|
+
File.join(DumpRake::RailsRoot, 'dump', file_name)
|
|
6
|
+
end
|
|
7
|
+
|
|
8
|
+
def new_dump(file_name)
|
|
9
|
+
DumpRake::Dump.new(dump_path(file_name))
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
describe "lock" do
|
|
13
|
+
before do
|
|
14
|
+
@yield_receiver = mock('yield_receiver')
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
it "should not yield if file does not exist" do
|
|
18
|
+
@yield_receiver.should_not_receive(:fire)
|
|
19
|
+
|
|
20
|
+
File.should_receive(:open).and_return(nil)
|
|
21
|
+
|
|
22
|
+
DumpRake::Dump.new('hello').lock do
|
|
23
|
+
@yield_receiver.fire
|
|
24
|
+
end
|
|
25
|
+
end
|
|
26
|
+
|
|
27
|
+
it "should not yield if file can not be locked" do
|
|
28
|
+
@yield_receiver.should_not_receive(:fire)
|
|
29
|
+
|
|
30
|
+
@file = mock('file')
|
|
31
|
+
@file.should_receive(:flock).with(File::LOCK_EX | File::LOCK_NB).and_return(nil)
|
|
32
|
+
@file.should_receive(:flock).with(File::LOCK_UN)
|
|
33
|
+
@file.should_receive(:close)
|
|
34
|
+
File.should_receive(:open).and_return(@file)
|
|
35
|
+
|
|
36
|
+
DumpRake::Dump.new('hello').lock do
|
|
37
|
+
@yield_receiver.fire
|
|
38
|
+
end
|
|
39
|
+
end
|
|
40
|
+
|
|
41
|
+
it "should yield if file can not be locked" do
|
|
42
|
+
@yield_receiver.should_receive(:fire)
|
|
43
|
+
|
|
44
|
+
@file = mock('file')
|
|
45
|
+
@file.should_receive(:flock).with(File::LOCK_EX | File::LOCK_NB).and_return(true)
|
|
46
|
+
@file.should_receive(:flock).with(File::LOCK_UN)
|
|
47
|
+
@file.should_receive(:close)
|
|
48
|
+
File.should_receive(:open).and_return(@file)
|
|
49
|
+
|
|
50
|
+
DumpRake::Dump.new('hello').lock do
|
|
51
|
+
@yield_receiver.fire
|
|
52
|
+
end
|
|
53
|
+
end
|
|
54
|
+
end
|
|
55
|
+
|
|
56
|
+
describe "new" do
|
|
57
|
+
it "should init with path if String sent" do
|
|
58
|
+
DumpRake::Dump.new('hello').path.should == Pathname('hello')
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
it "should init with path if Pathname sent" do
|
|
62
|
+
DumpRake::Dump.new(Pathname('hello')).path.should == Pathname('hello')
|
|
63
|
+
end
|
|
64
|
+
|
|
65
|
+
describe "with options" do
|
|
66
|
+
before do
|
|
67
|
+
@time = mock('time')
|
|
68
|
+
@time.stub!(:utc).and_return(@time)
|
|
69
|
+
@time.stub!(:strftime).and_return('19650414065945')
|
|
70
|
+
Time.stub!(:now).and_return(@time)
|
|
71
|
+
end
|
|
72
|
+
|
|
73
|
+
it "should generate path with no options" do
|
|
74
|
+
DumpRake::Dump.new.path.should == Pathname('19650414065945.tgz')
|
|
75
|
+
end
|
|
76
|
+
|
|
77
|
+
it "should generate with dir" do
|
|
78
|
+
DumpRake::Dump.new(:dir => 'dump_dir').path.should == Pathname('dump_dir/19650414065945.tgz')
|
|
79
|
+
end
|
|
80
|
+
|
|
81
|
+
it "should generate path with description" do
|
|
82
|
+
DumpRake::Dump.new(:dir => 'dump_dir', :desc => 'hello world').path.should == Pathname('dump_dir/19650414065945-hello world.tgz')
|
|
83
|
+
end
|
|
84
|
+
|
|
85
|
+
it "should generate path with tags" do
|
|
86
|
+
DumpRake::Dump.new(:dir => 'dump_dir', :tags => ' mirror, hello world ').path.should == Pathname('dump_dir/19650414065945@hello world,mirror.tgz')
|
|
87
|
+
end
|
|
88
|
+
|
|
89
|
+
it "should generate path with description and tags" do
|
|
90
|
+
DumpRake::Dump.new(:dir => 'dump_dir', :desc => 'Anniversary backup', :tags => ' mirror, hello world ').path.should == Pathname('dump_dir/19650414065945-Anniversary backup@hello world,mirror.tgz')
|
|
91
|
+
end
|
|
92
|
+
end
|
|
93
|
+
end
|
|
94
|
+
|
|
95
|
+
describe "versions" do
|
|
96
|
+
describe "list" do
|
|
97
|
+
def stub_glob
|
|
98
|
+
paths = %w[123 345 567].map do |name|
|
|
99
|
+
path = dump_path("#{name}.tgz")
|
|
100
|
+
File.should_receive(:file?).with(path).at_least(1).and_return(true)
|
|
101
|
+
path
|
|
102
|
+
end
|
|
103
|
+
Dir.stub!(:[]).and_return(paths)
|
|
104
|
+
end
|
|
105
|
+
|
|
106
|
+
it "should search for files in dump dir when asked for list" do
|
|
107
|
+
Dir.should_receive(:[]).with(dump_path('*.tgz')).and_return([])
|
|
108
|
+
DumpRake::Dump.list
|
|
109
|
+
end
|
|
110
|
+
|
|
111
|
+
it "should return selves instances for each found file" do
|
|
112
|
+
stub_glob
|
|
113
|
+
DumpRake::Dump.list.all?{ |dump| dump.should be_a(DumpRake::Dump) }
|
|
114
|
+
end
|
|
115
|
+
|
|
116
|
+
it "should return dumps with name containting :like" do
|
|
117
|
+
stub_glob
|
|
118
|
+
DumpRake::Dump.list(:like => '3').should == DumpRake::Dump.list.values_at(0, 1)
|
|
119
|
+
end
|
|
120
|
+
end
|
|
121
|
+
|
|
122
|
+
describe "with tags" do
|
|
123
|
+
before do
|
|
124
|
+
# 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
|
|
125
|
+
dumps_tags = [''] + %w[a a,d a,d,o a,d,s a,d,s,o a,o a,s a,s,o d d,o d,s d,s,o o s s,o z]
|
|
126
|
+
paths = dumps_tags.each_with_index.map do |dump_tags, i|
|
|
127
|
+
path = dump_path("196504140659#{10 + i}@#{dump_tags}.tgz")
|
|
128
|
+
File.should_receive(:file?).with(path).at_least(1).and_return(true)
|
|
129
|
+
path
|
|
130
|
+
end
|
|
131
|
+
Dir.stub!(:[]).and_return(paths)
|
|
132
|
+
end
|
|
133
|
+
|
|
134
|
+
it "should return all dumps if no tags send" do
|
|
135
|
+
DumpRake::Dump.list(:tags => '').should == DumpRake::Dump.list
|
|
136
|
+
end
|
|
137
|
+
|
|
138
|
+
{
|
|
139
|
+
'x' => [],
|
|
140
|
+
'+x' => [],
|
|
141
|
+
'z' => [16],
|
|
142
|
+
'a,d,s,o' => [1..15],
|
|
143
|
+
'+a,+d,+s,+o' => [5],
|
|
144
|
+
'-o' => [0, 1, 2, 4, 7, 9, 11, 14, 16],
|
|
145
|
+
'a,b,c,+s,-o' => [4, 7],
|
|
146
|
+
'+a,+d' => [2, 3, 4, 5],
|
|
147
|
+
'+d,+a' => [2, 3, 4, 5],
|
|
148
|
+
}.each do |tags, ids|
|
|
149
|
+
it "should return dumps filtered by #{tags}" do
|
|
150
|
+
DumpRake::Dump.list(:tags => tags).should == DumpRake::Dump.list.values_at(*ids)
|
|
151
|
+
end
|
|
152
|
+
end
|
|
153
|
+
end
|
|
154
|
+
end
|
|
155
|
+
|
|
156
|
+
describe "name" do
|
|
157
|
+
it "should return file name" do
|
|
158
|
+
new_dump("19650414065945.tgz").name.should == '19650414065945.tgz'
|
|
159
|
+
end
|
|
160
|
+
end
|
|
161
|
+
|
|
162
|
+
describe "parts" do
|
|
163
|
+
before do
|
|
164
|
+
@time = Time.utc(1965, 4, 14, 6, 59, 45)
|
|
165
|
+
end
|
|
166
|
+
|
|
167
|
+
def dump_name_parts(name)
|
|
168
|
+
dump = new_dump(name)
|
|
169
|
+
[dump.time, dump.description, dump.tags, dump.ext]
|
|
170
|
+
end
|
|
171
|
+
|
|
172
|
+
%w[tmp tgz].each do |ext|
|
|
173
|
+
it "should return empty results for dump with wrong name" do
|
|
174
|
+
dump_name_parts("196504140659.#{ext}").should == [nil, '', [], nil]
|
|
175
|
+
dump_name_parts("196504140659-lala.#{ext}").should == [nil, '', [], nil]
|
|
176
|
+
dump_name_parts("196504140659@lala.#{ext}").should == [nil, '', [], nil]
|
|
177
|
+
dump_name_parts("19650414065945.ops").should == [nil, '', [], nil]
|
|
178
|
+
end
|
|
179
|
+
|
|
180
|
+
it "should return tags for dump with tags" do
|
|
181
|
+
dump_name_parts("19650414065945.#{ext}").should == [@time, '', [], ext]
|
|
182
|
+
dump_name_parts("19650414065945- Hello world &&& .#{ext}").should == [@time, 'Hello world _', [], ext]
|
|
183
|
+
dump_name_parts("19650414065945- Hello world &&& @ test , hello world , bad tag ~~~~.#{ext}").should == [@time, 'Hello world _', ['bad tag _', 'hello world', 'test'], ext]
|
|
184
|
+
dump_name_parts("19650414065945@test, test , hello world , bad tag ~~~~.#{ext}").should == [@time, '', ['bad tag _', 'hello world', 'test'], ext]
|
|
185
|
+
dump_name_parts("19650414065945-Hello world@test,super tag.#{ext}").should == [@time, 'Hello world', ['super tag', 'test'], ext]
|
|
186
|
+
end
|
|
187
|
+
end
|
|
188
|
+
end
|
|
189
|
+
|
|
190
|
+
describe "path" do
|
|
191
|
+
it "should return path" do
|
|
192
|
+
new_dump("19650414065945.tgz").path.should == Pathname(File.join(DumpRake::RailsRoot, 'dump', "19650414065945.tgz"))
|
|
193
|
+
end
|
|
194
|
+
end
|
|
195
|
+
|
|
196
|
+
describe "tgz_path" do
|
|
197
|
+
it "should return path if extension is already tgz" do
|
|
198
|
+
new_dump("19650414065945.tgz").tgz_path.should == new_dump("19650414065945.tgz").path
|
|
199
|
+
end
|
|
200
|
+
|
|
201
|
+
it "should return path with tgz extension" do
|
|
202
|
+
new_dump("19650414065945.tmp").tgz_path.should == new_dump("19650414065945.tgz").path
|
|
203
|
+
end
|
|
204
|
+
end
|
|
205
|
+
|
|
206
|
+
describe "tmp_path" do
|
|
207
|
+
it "should return path if extension is already tmp" do
|
|
208
|
+
new_dump("19650414065945.tmp").tmp_path.should == new_dump("19650414065945.tmp").path
|
|
209
|
+
end
|
|
210
|
+
|
|
211
|
+
it "should return path with tmp extension" do
|
|
212
|
+
new_dump("19650414065945.tgz").tmp_path.should == new_dump("19650414065945.tmp").path
|
|
213
|
+
end
|
|
214
|
+
end
|
|
215
|
+
|
|
216
|
+
describe "clean_description" do
|
|
217
|
+
it "should shorten string to 50 chars and replace special symblos with '-'" do
|
|
218
|
+
DumpRake::Dump.new('').send(:clean_description, 'Special Dump #12837192837 (before fixind *&^*&^ photos)').should == 'Special Dump #12837192837 (before fixind _ photos)'
|
|
219
|
+
DumpRake::Dump.new('').send(:clean_description, "To#{'o' * 100} long description").should == "T#{'o' * 49}"
|
|
220
|
+
end
|
|
221
|
+
|
|
222
|
+
it "should accept non string" do
|
|
223
|
+
DumpRake::Dump.new('').send(:clean_description, nil).should == ''
|
|
224
|
+
end
|
|
225
|
+
end
|
|
226
|
+
|
|
227
|
+
describe "clean_tag" do
|
|
228
|
+
it "should shorten string to 20 chars and replace special symblos with '-'" do
|
|
229
|
+
DumpRake::Dump.new('').send(:clean_tag, 'Very special tag #12837192837 (fixind *&^*&^)').should == 'very special tag _12'
|
|
230
|
+
DumpRake::Dump.new('').send(:clean_tag, "To#{'o' * 100} long tag").should == "t#{'o' * 19}"
|
|
231
|
+
end
|
|
232
|
+
|
|
233
|
+
it "should not allow '-' or '+' to be first symbol" do
|
|
234
|
+
DumpRake::Dump.new('').send(:clean_tag, ' Very special tag').should == 'very special tag'
|
|
235
|
+
DumpRake::Dump.new('').send(:clean_tag, '-Very special tag').should == 'very special tag'
|
|
236
|
+
DumpRake::Dump.new('').send(:clean_tag, '-----------').should == ''
|
|
237
|
+
DumpRake::Dump.new('').send(:clean_tag, '+Very special tag').should == '_very special tag'
|
|
238
|
+
DumpRake::Dump.new('').send(:clean_tag, '+++++++++++').should == '_'
|
|
239
|
+
end
|
|
240
|
+
|
|
241
|
+
it "should accept non string" do
|
|
242
|
+
DumpRake::Dump.new('').send(:clean_tag, nil).should == ''
|
|
243
|
+
end
|
|
244
|
+
end
|
|
245
|
+
|
|
246
|
+
describe "clean_tags" do
|
|
247
|
+
it "should split string and return uniq non blank sorted tags" do
|
|
248
|
+
DumpRake::Dump.new('').send(:clean_tags, ' perfect tag , hello,Hello,this is (*^(*&').should == ['hello', 'perfect tag', 'this is _']
|
|
249
|
+
DumpRake::Dump.new('').send(:clean_tags, "l#{'o' * 100}ng tag").should == ["l#{'o' * 19}"]
|
|
250
|
+
end
|
|
251
|
+
|
|
252
|
+
it "should accept non string" do
|
|
253
|
+
DumpRake::Dump.new('').send(:clean_tags, nil).should == []
|
|
254
|
+
end
|
|
255
|
+
end
|
|
256
|
+
|
|
257
|
+
describe "get_filter_tags" do
|
|
258
|
+
it "should split string and return uniq non blank sorted tags" do
|
|
259
|
+
DumpRake::Dump.new('').send(:get_filter_tags, 'a,+b,+c,-d').should == {:simple => %w[a], :mandatory => %w[b c], :forbidden => %w[d]}
|
|
260
|
+
DumpRake::Dump.new('').send(:get_filter_tags, ' a , + b , + c , - d ').should == {:simple => %w[a], :mandatory => %w[b c], :forbidden => %w[d]}
|
|
261
|
+
DumpRake::Dump.new('').send(:get_filter_tags, ' a , + c , + b , - d ').should == {:simple => %w[a], :mandatory => %w[b c], :forbidden => %w[d]}
|
|
262
|
+
DumpRake::Dump.new('').send(:get_filter_tags, ' a , + b , + , - ').should == {:simple => %w[a], :mandatory => %w[b], :forbidden => []}
|
|
263
|
+
DumpRake::Dump.new('').send(:get_filter_tags, ' a , a , + b , + b , - d , - d ').should == {:simple => %w[a], :mandatory => %w[b], :forbidden => %w[d]}
|
|
264
|
+
proc{ DumpRake::Dump.new('').send(:get_filter_tags, 'a,+a') }.should_not raise_error
|
|
265
|
+
proc{ DumpRake::Dump.new('').send(:get_filter_tags, 'a,-a') }.should raise_error
|
|
266
|
+
proc{ DumpRake::Dump.new('').send(:get_filter_tags, '+a,-a') }.should raise_error
|
|
267
|
+
end
|
|
268
|
+
|
|
269
|
+
it "should accept non string" do
|
|
270
|
+
DumpRake::Dump.new('').send(:get_filter_tags, nil).should == {:simple => [], :mandatory => [], :forbidden => []}
|
|
271
|
+
end
|
|
272
|
+
end
|
|
273
|
+
|
|
274
|
+
describe "assets_root_link" do
|
|
275
|
+
it "should create tem dir, chdir there, symlink rails app root to assets, yield and unlink assets ever if something raised" do
|
|
276
|
+
Dir.should_receive(:mktmpdir).and_yield('/tmp/abc')
|
|
277
|
+
Dir.should_receive(:chdir).with('/tmp/abc').and_yield
|
|
278
|
+
File.should_receive(:symlink).with(DumpRake::RailsRoot, 'assets')
|
|
279
|
+
File.should_receive(:unlink).with('assets')
|
|
280
|
+
proc{
|
|
281
|
+
DumpRake::Dump.new('').send(:assets_root_link) do |dir, prefix|
|
|
282
|
+
dir.should == '/tmp/abc'
|
|
283
|
+
prefix.should == 'assets'
|
|
284
|
+
@yielded = true
|
|
285
|
+
raise 'just test'
|
|
286
|
+
end
|
|
287
|
+
}.should raise_error('just test')
|
|
288
|
+
@yielded.should == true
|
|
289
|
+
end
|
|
290
|
+
end
|
|
291
|
+
end
|
|
@@ -0,0 +1,328 @@
|
|
|
1
|
+
require File.dirname(__FILE__) + '/../../spec_helper'
|
|
2
|
+
|
|
3
|
+
require File.dirname(__FILE__) + '/../../../lib/dump_rake'
|
|
4
|
+
|
|
5
|
+
DumpWriter = DumpRake::DumpWriter
|
|
6
|
+
describe DumpWriter do
|
|
7
|
+
describe "create" do
|
|
8
|
+
it "should create selves instance and open" do
|
|
9
|
+
@dump = mock('dump')
|
|
10
|
+
@dump.should_receive(:open)
|
|
11
|
+
DumpWriter.should_receive(:new).with('/abc/123.tmp').and_return(@dump)
|
|
12
|
+
DumpWriter.create('/abc/123.tmp')
|
|
13
|
+
end
|
|
14
|
+
|
|
15
|
+
it "should call dump subroutines" do
|
|
16
|
+
@dump = mock('dump')
|
|
17
|
+
@dump.stub!(:open).and_yield(@dump)
|
|
18
|
+
DumpWriter.stub!(:new).and_return(@dump)
|
|
19
|
+
|
|
20
|
+
@dump.should_receive(:write_schema).ordered
|
|
21
|
+
@dump.should_receive(:write_tables).ordered
|
|
22
|
+
@dump.should_receive(:write_assets).ordered
|
|
23
|
+
@dump.should_receive(:write_config).ordered
|
|
24
|
+
|
|
25
|
+
DumpWriter.create('/abc/123.tmp')
|
|
26
|
+
end
|
|
27
|
+
end
|
|
28
|
+
|
|
29
|
+
describe "open" do
|
|
30
|
+
it "should create dir for dump" do
|
|
31
|
+
Zlib::GzipWriter.stub!(:open)
|
|
32
|
+
FileUtils.should_receive(:mkpath).with('/abc/def/ghi')
|
|
33
|
+
DumpWriter.new('/abc/def/ghi/123.tgz').open
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
it "should set stream to gzipped tar writer" do
|
|
37
|
+
FileUtils.stub!(:mkpath)
|
|
38
|
+
@gzip = mock('gzip')
|
|
39
|
+
@stream = mock('stream')
|
|
40
|
+
Zlib::GzipWriter.should_receive(:open).with(Pathname("123.tgz")).and_yield(@gzip)
|
|
41
|
+
Archive::Tar::Minitar::Output.should_receive(:open).with(@gzip).and_yield(@stream)
|
|
42
|
+
@gzip.should_receive(:mtime=).with(Time.utc(2000))
|
|
43
|
+
|
|
44
|
+
@dump = DumpWriter.new('123.tgz')
|
|
45
|
+
@dump.should_receive(:lock).and_yield
|
|
46
|
+
@dump.open do |dump|
|
|
47
|
+
dump.should == @dump
|
|
48
|
+
dump.stream.should == @stream
|
|
49
|
+
end
|
|
50
|
+
end
|
|
51
|
+
end
|
|
52
|
+
|
|
53
|
+
describe "subroutines" do
|
|
54
|
+
before do
|
|
55
|
+
@tar = mock('tar')
|
|
56
|
+
@stream = mock('stream', :tar => @tar)
|
|
57
|
+
@config = {:tables => {}}
|
|
58
|
+
@dump = DumpWriter.new('123.tgz')
|
|
59
|
+
@dump.stub!(:stream).and_return(@stream)
|
|
60
|
+
@dump.stub!(:config).and_return(@config)
|
|
61
|
+
Progress.stub!(:io).and_return(StringIO.new)
|
|
62
|
+
end
|
|
63
|
+
|
|
64
|
+
describe "create_file" do
|
|
65
|
+
it "should create temp file, yield it for writing, create file in tar and write it there" do
|
|
66
|
+
@temp = mock('temp', :open => true, :length => 6, :read => 'qwfpgj')
|
|
67
|
+
@temp.should_receive(:write).with('qwfpgj')
|
|
68
|
+
@temp.stub!(:eof?).and_return(false, true)
|
|
69
|
+
Tempfile.should_receive(:open).and_yield(@temp)
|
|
70
|
+
|
|
71
|
+
@file = mock('file')
|
|
72
|
+
@file.should_receive(:write).with('qwfpgj')
|
|
73
|
+
|
|
74
|
+
@stream.tar.should_receive(:add_file_simple).with('abc/def.txt', :mode => 0100444, :size => 6).and_yield(@file)
|
|
75
|
+
|
|
76
|
+
@dump.create_file('abc/def.txt') do |file|
|
|
77
|
+
file.should == @temp
|
|
78
|
+
file.write('qwfpgj')
|
|
79
|
+
end
|
|
80
|
+
end
|
|
81
|
+
end
|
|
82
|
+
|
|
83
|
+
describe "write_schema" do
|
|
84
|
+
it "should create file schema.rb" do
|
|
85
|
+
@dump.should_receive(:create_file).with('schema.rb')
|
|
86
|
+
@dump.write_schema
|
|
87
|
+
end
|
|
88
|
+
|
|
89
|
+
it "should set ENV[SCHEMA] to path of returned file" do
|
|
90
|
+
@file = mock('file', :path => 'db/schema.rb')
|
|
91
|
+
@dump.stub!(:create_file).and_yield(@file)
|
|
92
|
+
DumpRake::Env.should_receive(:with_env).with('SCHEMA' => 'db/schema.rb')
|
|
93
|
+
@dump.write_schema
|
|
94
|
+
end
|
|
95
|
+
|
|
96
|
+
it "should call rake task db:schema:dump" do
|
|
97
|
+
@file = mock('file', :path => 'db/schema.rb')
|
|
98
|
+
@dump.stub!(:create_file).and_yield(@file)
|
|
99
|
+
@task = mock('task')
|
|
100
|
+
Rake::Task.should_receive(:[]).with('db:schema:dump').and_return(@task)
|
|
101
|
+
@task.should_receive(:invoke)
|
|
102
|
+
@dump.write_schema
|
|
103
|
+
end
|
|
104
|
+
end
|
|
105
|
+
|
|
106
|
+
describe "write_tables" do
|
|
107
|
+
it "should verify connection" do
|
|
108
|
+
@dump.stub!(:tables_to_dump).and_return([])
|
|
109
|
+
@dump.should_receive(:verify_connection)
|
|
110
|
+
@dump.write_tables
|
|
111
|
+
end
|
|
112
|
+
|
|
113
|
+
it "should call write_table for each table returned by tables_to_dump" do
|
|
114
|
+
@dump.stub!(:verify_connection)
|
|
115
|
+
@dump.stub!(:tables_to_dump).and_return(%w[first second])
|
|
116
|
+
|
|
117
|
+
@dump.should_receive(:write_table).with('first')
|
|
118
|
+
@dump.should_receive(:write_table).with('second')
|
|
119
|
+
|
|
120
|
+
@dump.write_tables
|
|
121
|
+
end
|
|
122
|
+
end
|
|
123
|
+
|
|
124
|
+
describe "write_table" do
|
|
125
|
+
it "should get row count and store it to config" do
|
|
126
|
+
@dump.should_receive(:table_row_count).with('first').and_return(666)
|
|
127
|
+
@dump.stub!(:create_file)
|
|
128
|
+
@dump.write_table('first')
|
|
129
|
+
@config[:tables]['first'].should == 666
|
|
130
|
+
end
|
|
131
|
+
|
|
132
|
+
it "should create_file" do
|
|
133
|
+
@dump.stub!(:table_row_count).and_return(666)
|
|
134
|
+
@dump.should_receive(:create_file)
|
|
135
|
+
@dump.write_table('first')
|
|
136
|
+
end
|
|
137
|
+
|
|
138
|
+
it "should dump column names and values of each row" do
|
|
139
|
+
@column_definitions = [
|
|
140
|
+
mock('column', :name => 'id'),
|
|
141
|
+
mock('column', :name => 'name'),
|
|
142
|
+
mock('column', :name => 'associated_id')
|
|
143
|
+
]
|
|
144
|
+
ActiveRecord::Base.connection.stub!(:columns).and_return(@column_definitions)
|
|
145
|
+
@rows = [
|
|
146
|
+
{'id' => 1, 'name' => 'a', 'associated_id' => 100},
|
|
147
|
+
{'id' => 2, 'name' => 'b', 'associated_id' => 666},
|
|
148
|
+
]
|
|
149
|
+
|
|
150
|
+
@file = mock('file')
|
|
151
|
+
@dump.stub!(:table_row_count).and_return(666)
|
|
152
|
+
@dump.stub!(:create_file).and_yield(@file)
|
|
153
|
+
|
|
154
|
+
column_names = @column_definitions.map(&:name).sort
|
|
155
|
+
@file.should_receive(:write).with(Marshal.dump(column_names)).ordered
|
|
156
|
+
each_tabler_row_yielder = @dump.should_receive(:each_table_row)
|
|
157
|
+
@rows.each do |row|
|
|
158
|
+
each_tabler_row_yielder.and_yield(row)
|
|
159
|
+
@file.should_receive(:write).with(Marshal.dump(row.values_at(*column_names))).ordered
|
|
160
|
+
@column_definitions.each do |column_definition|
|
|
161
|
+
column_definition.should_receive(:type_cast).with(row[column_definition.name]).and_return(row[column_definition.name])
|
|
162
|
+
end
|
|
163
|
+
end
|
|
164
|
+
|
|
165
|
+
@dump.write_table('first')
|
|
166
|
+
end
|
|
167
|
+
end
|
|
168
|
+
|
|
169
|
+
describe "write_assets" do
|
|
170
|
+
before do
|
|
171
|
+
@dump.stub!(:assets_root_link).and_yield('/tmp', 'assets')
|
|
172
|
+
end
|
|
173
|
+
|
|
174
|
+
it "should call assets_to_dump" do
|
|
175
|
+
@dump.should_receive(:assets_to_dump).and_return([])
|
|
176
|
+
@dump.write_assets
|
|
177
|
+
end
|
|
178
|
+
|
|
179
|
+
it "should change root to rails app root" do
|
|
180
|
+
@file = mock('file')
|
|
181
|
+
@dump.stub!(:assets_to_dump).and_return(%w[images videos])
|
|
182
|
+
@dump.stub!(:create_file).and_yield(@file)
|
|
183
|
+
|
|
184
|
+
Dir.should_receive(:chdir).with(DumpRake::RailsRoot)
|
|
185
|
+
@dump.write_assets
|
|
186
|
+
end
|
|
187
|
+
|
|
188
|
+
it "should put assets to config" do
|
|
189
|
+
@file = mock('file')
|
|
190
|
+
@dump.stub!(:assets_to_dump).and_return(%w[images/* videos])
|
|
191
|
+
@dump.stub!(:create_file).and_yield(@file)
|
|
192
|
+
Dir.stub!(:chdir).and_yield
|
|
193
|
+
@tar = mock('tar_writer')
|
|
194
|
+
Archive::Tar::Minitar::Output.stub!(:open).and_yield(@tar)
|
|
195
|
+
Dir.stub!(:[]).and_return([])
|
|
196
|
+
Dir.should_receive(:[]).with(*%w[images/* videos]).and_return(%w[images/a images/b videos])
|
|
197
|
+
|
|
198
|
+
@dump.write_assets
|
|
199
|
+
counts = {:files => 0, :total => 0}
|
|
200
|
+
@config[:assets].should == {'images/a' => counts, 'images/b' => counts, 'videos' => counts}
|
|
201
|
+
end
|
|
202
|
+
|
|
203
|
+
it "should use glob to find files" do
|
|
204
|
+
@file = mock('file')
|
|
205
|
+
@dump.stub!(:assets_to_dump).and_return(%w[images/* videos])
|
|
206
|
+
@dump.stub!(:create_file).and_yield(@file)
|
|
207
|
+
Dir.stub!(:chdir).and_yield
|
|
208
|
+
@tar = mock('tar_writer')
|
|
209
|
+
Archive::Tar::Minitar::Output.stub!(:open).and_yield(@tar)
|
|
210
|
+
|
|
211
|
+
Dir.should_receive(:[]).with(*%w[images/* videos]).and_return(%w[images/a images/b videos])
|
|
212
|
+
Dir.should_receive(:[]).with('images/a/**/*').and_return([])
|
|
213
|
+
Dir.should_receive(:[]).with('images/b/**/*').and_return([])
|
|
214
|
+
Dir.should_receive(:[]).with('videos/**/*').and_return([])
|
|
215
|
+
|
|
216
|
+
@dump.write_assets
|
|
217
|
+
end
|
|
218
|
+
|
|
219
|
+
it "should pack each file from assets_root_link" do
|
|
220
|
+
@file = mock('file')
|
|
221
|
+
@dump.stub!(:assets_to_dump).and_return(%w[images/* videos])
|
|
222
|
+
@dump.stub!(:create_file).and_yield(@file)
|
|
223
|
+
Dir.stub!(:chdir).and_yield
|
|
224
|
+
@tar = mock('tar_writer')
|
|
225
|
+
Archive::Tar::Minitar::Output.stub!(:open).and_yield(@tar)
|
|
226
|
+
|
|
227
|
+
Dir.should_receive(:[]).with(*%w[images/* videos]).and_return(%w[images/a images/b videos])
|
|
228
|
+
Dir.should_receive(:[]).with('images/a/**/*').and_return([])
|
|
229
|
+
Dir.should_receive(:[]).with('images/b/**/*').and_return([])
|
|
230
|
+
Dir.should_receive(:[]).with('videos/**/*').and_return([])
|
|
231
|
+
|
|
232
|
+
@dump.should_receive(:assets_root_link).exactly(3).times
|
|
233
|
+
|
|
234
|
+
@dump.write_assets
|
|
235
|
+
end
|
|
236
|
+
|
|
237
|
+
it "should pack each file" do
|
|
238
|
+
@file = mock('file')
|
|
239
|
+
@dump.stub!(:assets_to_dump).and_return(%w[images/* videos])
|
|
240
|
+
@dump.stub!(:create_file).and_yield(@file)
|
|
241
|
+
Dir.stub!(:chdir).and_yield
|
|
242
|
+
@tar = mock('tar_writer')
|
|
243
|
+
Archive::Tar::Minitar::Output.stub!(:open).and_yield(@tar)
|
|
244
|
+
|
|
245
|
+
Dir.should_receive(:[]).with(*%w[images/* videos]).and_return(%w[images/a images/b videos])
|
|
246
|
+
Dir.should_receive(:[]).with('images/a/**/*').and_return(%w[a.jpg b.jpg])
|
|
247
|
+
Dir.should_receive(:[]).with('images/b/**/*').and_return(%w[c.jpg d.jpg])
|
|
248
|
+
Dir.should_receive(:[]).with('videos/**/*').and_return(%w[a.mov b.mov])
|
|
249
|
+
|
|
250
|
+
%w[a.jpg b.jpg c.jpg d.jpg a.mov b.mov].each do |file_name|
|
|
251
|
+
Archive::Tar::Minitar.should_receive(:pack_file).with("assets/#{file_name}", @stream)
|
|
252
|
+
end
|
|
253
|
+
|
|
254
|
+
@dump.write_assets
|
|
255
|
+
end
|
|
256
|
+
|
|
257
|
+
it "should not raise if something fails when packing" do
|
|
258
|
+
@file = mock('file')
|
|
259
|
+
@dump.stub!(:assets_to_dump).and_return(%w[videos])
|
|
260
|
+
@dump.stub!(:create_file).and_yield(@file)
|
|
261
|
+
Dir.stub!(:chdir).and_yield
|
|
262
|
+
@tar = mock('tar_writer')
|
|
263
|
+
Archive::Tar::Minitar::Output.stub!(:open).and_yield(@tar)
|
|
264
|
+
|
|
265
|
+
Dir.should_receive(:[]).with(*%w[videos]).and_return(%w[videos])
|
|
266
|
+
Dir.should_receive(:[]).with('videos/**/*').and_return(%w[a.mov b.mov])
|
|
267
|
+
|
|
268
|
+
Archive::Tar::Minitar.should_receive(:pack_file).with('assets/a.mov', @stream).and_raise('file not found')
|
|
269
|
+
Archive::Tar::Minitar.should_receive(:pack_file).with('assets/b.mov', @stream)
|
|
270
|
+
|
|
271
|
+
grab_output {
|
|
272
|
+
@dump.write_assets
|
|
273
|
+
}
|
|
274
|
+
end
|
|
275
|
+
|
|
276
|
+
end
|
|
277
|
+
|
|
278
|
+
describe "write_config" do
|
|
279
|
+
it "should create file config" do
|
|
280
|
+
@dump.should_receive(:create_file).with('config')
|
|
281
|
+
@dump.write_config
|
|
282
|
+
end
|
|
283
|
+
|
|
284
|
+
it "should dump column names and values of each row" do
|
|
285
|
+
@file = mock('file')
|
|
286
|
+
@dump.stub!(:create_file).and_yield(@file)
|
|
287
|
+
@config.replace({:tables => {'first' => 1, 'second' => 2}, :assets => %w[images videos]})
|
|
288
|
+
|
|
289
|
+
@file.should_receive(:write).with(Marshal.dump(@config))
|
|
290
|
+
@dump.write_config
|
|
291
|
+
end
|
|
292
|
+
end
|
|
293
|
+
|
|
294
|
+
describe "assets_to_dump" do
|
|
295
|
+
it "should call rake task assets" do
|
|
296
|
+
@task = mock('task')
|
|
297
|
+
Rake::Task.should_receive(:[]).with('assets').and_return(@task)
|
|
298
|
+
@task.should_receive(:invoke)
|
|
299
|
+
@dump.assets_to_dump
|
|
300
|
+
end
|
|
301
|
+
|
|
302
|
+
it "should return array of assets if separator is colon" do
|
|
303
|
+
@task = mock('task')
|
|
304
|
+
Rake::Task.stub!(:[]).and_return(@task)
|
|
305
|
+
@task.stub!(:invoke)
|
|
306
|
+
DumpRake::Env.with_env(:assets => 'images:videos') do
|
|
307
|
+
@dump.assets_to_dump.should == %w[images videos]
|
|
308
|
+
end
|
|
309
|
+
end
|
|
310
|
+
|
|
311
|
+
it "should return array of assets if separator is comma" do
|
|
312
|
+
@task = mock('task')
|
|
313
|
+
Rake::Task.stub!(:[]).and_return(@task)
|
|
314
|
+
@task.stub!(:invoke)
|
|
315
|
+
DumpRake::Env.with_env(:assets => 'images,videos') do
|
|
316
|
+
@dump.assets_to_dump.should == %w[images videos]
|
|
317
|
+
end
|
|
318
|
+
end
|
|
319
|
+
|
|
320
|
+
it "should return empty array if calling rake task assets raises an exception" do
|
|
321
|
+
Rake::Task.stub!(:[]).and_raise('task assets not found')
|
|
322
|
+
DumpRake::Env.with_env(:assets => 'images:videos') do
|
|
323
|
+
@dump.assets_to_dump.should == []
|
|
324
|
+
end
|
|
325
|
+
end
|
|
326
|
+
end
|
|
327
|
+
end
|
|
328
|
+
end
|