darkofabijan-astrails-safe 0.2.8

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.
Files changed (41) hide show
  1. data/LICENSE +20 -0
  2. data/README.markdown +237 -0
  3. data/Rakefile +61 -0
  4. data/bin/astrails-safe +53 -0
  5. data/examples/example_helper.rb +19 -0
  6. data/lib/astrails/safe.rb +61 -0
  7. data/lib/astrails/safe/archive.rb +24 -0
  8. data/lib/astrails/safe/backup.rb +20 -0
  9. data/lib/astrails/safe/cloudfiles.rb +70 -0
  10. data/lib/astrails/safe/config/builder.rb +60 -0
  11. data/lib/astrails/safe/config/node.rb +76 -0
  12. data/lib/astrails/safe/gpg.rb +46 -0
  13. data/lib/astrails/safe/gzip.rb +25 -0
  14. data/lib/astrails/safe/local.rb +70 -0
  15. data/lib/astrails/safe/mysqldump.rb +32 -0
  16. data/lib/astrails/safe/pgdump.rb +36 -0
  17. data/lib/astrails/safe/pipe.rb +17 -0
  18. data/lib/astrails/safe/s3.rb +86 -0
  19. data/lib/astrails/safe/sftp.rb +88 -0
  20. data/lib/astrails/safe/sink.rb +35 -0
  21. data/lib/astrails/safe/source.rb +47 -0
  22. data/lib/astrails/safe/stream.rb +20 -0
  23. data/lib/astrails/safe/svndump.rb +13 -0
  24. data/lib/astrails/safe/tmp_file.rb +48 -0
  25. data/lib/extensions/mktmpdir.rb +45 -0
  26. data/spec/integration/archive_integration_spec.rb +88 -0
  27. data/spec/integration/cleanup_spec.rb +61 -0
  28. data/spec/spec.opts +5 -0
  29. data/spec/spec_helper.rb +16 -0
  30. data/spec/unit/archive_spec.rb +67 -0
  31. data/spec/unit/cloudfiles_spec.rb +170 -0
  32. data/spec/unit/config_spec.rb +213 -0
  33. data/spec/unit/gpg_spec.rb +148 -0
  34. data/spec/unit/gzip_spec.rb +64 -0
  35. data/spec/unit/local_spec.rb +110 -0
  36. data/spec/unit/mysqldump_spec.rb +83 -0
  37. data/spec/unit/pgdump_spec.rb +45 -0
  38. data/spec/unit/s3_spec.rb +160 -0
  39. data/spec/unit/svndump_spec.rb +39 -0
  40. data/templates/script.rb +165 -0
  41. metadata +179 -0
@@ -0,0 +1,160 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
2
+
3
+ describe Astrails::Safe::S3 do
4
+
5
+ def def_config
6
+ {
7
+ :s3 => {
8
+ :bucket => "_bucket",
9
+ :key => "_key",
10
+ :secret => "_secret",
11
+ },
12
+ :keep => {
13
+ :s3 => 2
14
+ }
15
+ }
16
+ end
17
+
18
+ def def_backup(extra = {})
19
+ {
20
+ :kind => "_kind",
21
+ :filename => "/backup/somewhere/_kind-_id.NOW.bar",
22
+ :extension => ".bar",
23
+ :id => "_id",
24
+ :timestamp => "NOW"
25
+ }.merge(extra)
26
+ end
27
+
28
+ def s3(config = def_config, backup = def_backup)
29
+ Astrails::Safe::S3.new(
30
+ Astrails::Safe::Config::Node.new(nil, config),
31
+ Astrails::Safe::Backup.new(backup)
32
+ )
33
+ end
34
+
35
+ describe :cleanup do
36
+
37
+ before(:each) do
38
+ @s3 = s3
39
+
40
+ @files = [4,1,3,2].to_a.map { |i| stub(o = {}).key {"aaaaa#{i}"}; o }
41
+
42
+ stub(AWS::S3::Bucket).objects("_bucket", :prefix => "_kind/_id/_kind-_id.", :max_keys => 4) {@files}
43
+ stub(AWS::S3::Bucket).find("_bucket").stub![anything].stub!.delete
44
+ end
45
+
46
+ it "should check [:keep, :s3]" do
47
+ @s3.config[:keep].data["s3"] = nil
48
+ dont_allow(@s3.backup).filename
49
+ @s3.send :cleanup
50
+ end
51
+
52
+ it "should delete extra files" do
53
+ mock(AWS::S3::Bucket).find("_bucket").mock!["aaaaa1"].mock!.delete
54
+ mock(AWS::S3::Bucket).find("_bucket").mock!["aaaaa2"].mock!.delete
55
+ @s3.send :cleanup
56
+ end
57
+
58
+ end
59
+
60
+ describe :active do
61
+ before(:each) do
62
+ @s3 = s3
63
+ end
64
+
65
+ it "should be true when all params are set" do
66
+ @s3.should be_active
67
+ end
68
+
69
+ it "should be false if bucket is missing" do
70
+ @s3.config[:s3].data["bucket"] = nil
71
+ @s3.should_not be_active
72
+ end
73
+
74
+ it "should be false if key is missing" do
75
+ @s3.config[:s3].data["key"] = nil
76
+ @s3.should_not be_active
77
+ end
78
+
79
+ it "should be false if secret is missing" do
80
+ @s3.config[:s3].data["secret"] = nil
81
+ @s3.should_not be_active
82
+ end
83
+ end
84
+
85
+ describe :path do
86
+ before(:each) do
87
+ @s3 = s3
88
+ end
89
+ it "should use s3/path 1st" do
90
+ @s3.config[:s3].data["path"] = "s3_path"
91
+ @s3.config[:local] = {:path => "local_path"}
92
+ @s3.send(:path).should == "s3_path"
93
+ end
94
+
95
+ it "should use local/path 2nd" do
96
+ @s3.config[:local] = {:path => "local_path"}
97
+ @s3.send(:path).should == "local_path"
98
+ end
99
+
100
+ it "should use constant 3rd" do
101
+ @s3.send(:path).should == "_kind/_id"
102
+ end
103
+
104
+ end
105
+
106
+ describe :save do
107
+ def add_stubs(*stubs)
108
+ stubs.each do |s|
109
+ case s
110
+ when :connection
111
+ stub(AWS::S3::Base).establish_connection!(:access_key_id => "_key", :secret_access_key => "_secret", :use_ssl => true)
112
+ when :stat
113
+ stub(File).stat("foo").stub!.size {123}
114
+ when :create_bucket
115
+ stub(AWS::S3::Bucket).create
116
+ when :file_open
117
+ stub(File).open("foo") {|f, block| block.call(:opened_file)}
118
+ when :s3_store
119
+ stub(AWS::S3::S3Object).store(@full_path, :opened_file, "_bucket")
120
+ end
121
+ end
122
+ end
123
+
124
+ before(:each) do
125
+ @s3 = s3(def_config, def_backup(:path => "foo"))
126
+ @full_path = "_kind/_id/backup/somewhere/_kind-_id.NOW.bar.bar"
127
+ end
128
+
129
+ it "should fail if no backup.file is set" do
130
+ @s3.backup.path = nil
131
+ proc {@s3.send(:save)}.should raise_error(RuntimeError)
132
+ end
133
+
134
+ it "should establish s3 connection" do
135
+ mock(AWS::S3::Base).establish_connection!(:access_key_id => "_key", :secret_access_key => "_secret", :use_ssl => true)
136
+ add_stubs(:stat, :create_bucket, :file_open, :s3_store)
137
+ @s3.send(:save)
138
+ end
139
+
140
+ it "should open local file" do
141
+ add_stubs(:connection, :stat, :create_bucket)
142
+ mock(File).open("foo")
143
+ @s3.send(:save)
144
+ end
145
+
146
+ it "should upload file" do
147
+ add_stubs(:connection, :stat, :create_bucket, :file_open)
148
+ mock(AWS::S3::S3Object).store(@full_path, :opened_file, "_bucket")
149
+ @s3.send(:save)
150
+ end
151
+
152
+ it "should fail on files bigger then 5G" do
153
+ add_stubs(:connection)
154
+ mock(File).stat("foo").stub!.size {5*1024*1024*1024+1}
155
+ mock(STDERR).puts(anything)
156
+ dont_allow(Benchmark).realtime
157
+ @s3.send(:save)
158
+ end
159
+ end
160
+ end
@@ -0,0 +1,39 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
2
+
3
+ describe Astrails::Safe::Svndump do
4
+ def def_config
5
+ {
6
+ :options => "OPTS",
7
+ :repo_path => "bar/baz"
8
+ }
9
+ end
10
+
11
+ def svndump(id = :foo, config = def_config)
12
+ Astrails::Safe::Svndump.new(id, Astrails::Safe::Config::Node.new(nil, config))
13
+ end
14
+
15
+ before(:each) do
16
+ stub(Time).now.stub!.strftime {"NOW"}
17
+ end
18
+
19
+ after(:each) { Astrails::Safe::TmpFile.cleanup }
20
+
21
+ describe :backup do
22
+ before(:each) do
23
+ @svn = svndump
24
+ end
25
+
26
+ {
27
+ :id => "foo",
28
+ :kind => "svndump",
29
+ :extension => ".svn",
30
+ :filename => "svndump-foo.NOW",
31
+ :command => "svnadmin dump OPTS bar/baz",
32
+ }.each do |k, v|
33
+ it "should set #{k} to #{v}" do
34
+ @svn.backup.send(k).should == v
35
+ end
36
+ end
37
+
38
+ end
39
+ end
@@ -0,0 +1,165 @@
1
+ safe do
2
+
3
+ # backup file path (not including filename)
4
+ # supported substitutions:
5
+ # :kind -> backup 'engine' kind, e.g. "mysqldump" or "archive"
6
+ # :id -> backup 'id', e.g. "blog", "production", etc.
7
+ # :timestamp -> current run timestamp (same for all the backups in the same 'run')
8
+ # you can set separate :path for all backups (or once globally here)
9
+ local do
10
+ path "/backup/:kind"
11
+ end
12
+
13
+ ## uncomment to enable uploads to Amazon S3
14
+ ## Amazon S3 auth (optional)
15
+ # s3 do
16
+ # key YOUR_S3_KEY
17
+ # secret YOUR_S3_SECRET
18
+ # bucket S3_BUCKET
19
+ # # path for uploads to S3. supports same substitution like :local/:path
20
+ # path ":kind/" # this is default
21
+ # end
22
+
23
+ ## alternative style:
24
+ # s3 :key => YOUR_S3_KEY, :secret => YOUR_S3_SECRET, :bucket => S3_BUCKET, :path => ":kind/"
25
+
26
+ ## uncomment to enable uploads to Rackspace Cloud Files
27
+ ## http://www.rackspacecloud.com/cloud_hosting_products/files
28
+ ## Rackspace auth (optional)
29
+ # cloudfiles do
30
+ # user "YOUR_RACKSPACE_CLOUD_USERNAME"
31
+ # api_key "YOUR_RACKSPACE_API_KEY"
32
+ # container "YOUR_CONTAINER_NAME"
33
+ # # path for uploads to Cloud Files, supports same substitution like :local/:path
34
+ # path ":kind/" # this is default
35
+ # # If you are running the backup from a system within the Rackspace/Slicehost network and would like
36
+ # # to back up over the private (unbilled) service net, set this value to true.
37
+ # # service_net true
38
+ # end
39
+
40
+ ## uncomment to enable uploads via SFTP
41
+ # sftp do
42
+ # host "YOUR_REMOTE_HOSTNAME"
43
+ # user "YOUR_REMOTE_USERNAME"
44
+ # # port "NON STANDARD SSH PORT"
45
+ # password "YOUR_REMOTE_PASSWORD"
46
+ # path ":kind/:id" # this is the default
47
+ # end
48
+
49
+ ## uncomment to enable GPG encryption.
50
+ ## Note: you can use public 'key' or symmetric password but not both!
51
+ # gpg do
52
+ # # you can specify your own gpg executable with the 'command' options
53
+ # # this can be useful for example to choose b/w gpg and gpg2 if both are installed
54
+ # # some gpg installations will automatically set 'use-agent' option in the
55
+ # # config file on the 1st run. see README for more details
56
+ # options "--no-use-agent"
57
+ # # command "/usr/local/bin/gpg"
58
+ # # key "backup@astrails.com"
59
+ # password "astrails"
60
+ # end
61
+
62
+ ## uncomment to enable backup rotation. keep only given number of latest
63
+ ## backups. remove the rest
64
+ # keep do
65
+ # local 4 # keep 4 local backups
66
+ # s3 20 # keep 20 S3 backups
67
+ # end
68
+
69
+ # Paging config
70
+ page do
71
+ page_size 1048576 # 1Mb
72
+ end
73
+
74
+ # backup mysql databases with mysqldump
75
+ mysqldump do
76
+ # you can override any setting from parent in a child:
77
+ options "-ceKq --single-transaction --create-options"
78
+
79
+ user "astrails"
80
+ password ""
81
+ # host "localhost"
82
+ # port 3306
83
+ socket "/var/run/mysqld/mysqld.sock"
84
+
85
+ # database is a 'collection' element. it must have a hash or block parameter
86
+ # it will be 'collected' in a 'databases', with database id (1st arg) used as hash key
87
+ # the following code will create mysqldump/databases/blog and mysqldump/databases/mysql ocnfiguration 'nodes'
88
+
89
+ # backup database with default values
90
+ # database :blog
91
+
92
+ # backup overriding some values
93
+ # database :production do
94
+ # # you can override 'partially'
95
+ # keep :local => 3
96
+ # # keep/local is 3, and keep/s3 is 20 (from parent)
97
+
98
+ # # local override for gpg password
99
+ # gpg do
100
+ # password "custom-production-pass"
101
+ # end
102
+ # # skip those tables during backup
103
+ # # you can pass an array
104
+ # skip_tables [:logger_exceptions, :request_logs]
105
+ # # or pass them all separately
106
+ # skip_tables :test1
107
+ # skip_tables :test2
108
+ # end
109
+
110
+ end
111
+
112
+ # # uncomment to enable
113
+ # # backup PostgreSQL databases with pg_dump
114
+ # pgdump do
115
+ # options "-i -x -O"
116
+ #
117
+ # user "markmansour"
118
+ # # password "" - leave this out if you have ident setup
119
+ #
120
+ # # database is a 'collection' element. it must have a hash or block parameter
121
+ # # it will be 'collected' in a 'databases', with database id (1st arg) used as hash key
122
+ # database :blog
123
+ # database :production
124
+ # end
125
+
126
+ tar do
127
+ # options "-h" # uncomment this to dereference symbolic links
128
+
129
+ # 'archive' is a collection item, just like 'database'
130
+ # archive "git-repositories" do
131
+ # # files and directories to backup
132
+ # files "/home/git/repositories"
133
+ # # can have more then one 'files' lines or/and use an array
134
+ # files ["/home/dev/work/foo", "/home/dev/work/bar"]
135
+ # end
136
+
137
+ # archive "etc-files" do
138
+ # files "/etc"
139
+ # # exlude those files/directories
140
+ # exclude "/etc/puppet/other"
141
+ # # can have multiple 'exclude' lines or/and use an array
142
+ # exclude ["/etc/tmp/a", "/etc/tmp/b"]
143
+ # end
144
+
145
+ # archive "dot-configs" do
146
+ # files "/home/*/.[^.]*"
147
+ # end
148
+
149
+ # archive "blog" do
150
+ # files "/var/www/blog.astrails.com/"
151
+ # # specify multiple files/directories as array
152
+ # exclude ["/var/www/blog.astrails.com/log", "/var/www/blog.astrails.com/tmp"]
153
+ # end
154
+
155
+ # archive "site" do
156
+ # files "/var/www/astrails.com/"
157
+ # exclude ["/var/www/astrails.com/log", "/var/www/astrails.com/tmp"]
158
+ # end
159
+
160
+ # archive :misc do
161
+ # files [ "/backup/*.rb" ]
162
+ # end
163
+ end
164
+
165
+ end
metadata ADDED
@@ -0,0 +1,179 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: darkofabijan-astrails-safe
3
+ version: !ruby/object:Gem::Version
4
+ hash: 7
5
+ prerelease: false
6
+ segments:
7
+ - 0
8
+ - 2
9
+ - 8
10
+ version: 0.2.8
11
+ platform: ruby
12
+ authors:
13
+ - Astrails Ltd.
14
+ autorequire:
15
+ bindir: bin
16
+ cert_chain: []
17
+
18
+ date: 2010-02-17 00:00:00 +01:00
19
+ default_executable: astrails-safe
20
+ dependencies:
21
+ - !ruby/object:Gem::Dependency
22
+ name: aws-s3
23
+ prerelease: false
24
+ requirement: &id001 !ruby/object:Gem::Requirement
25
+ none: false
26
+ requirements:
27
+ - - ">="
28
+ - !ruby/object:Gem::Version
29
+ hash: 3
30
+ segments:
31
+ - 0
32
+ version: "0"
33
+ type: :runtime
34
+ version_requirements: *id001
35
+ - !ruby/object:Gem::Dependency
36
+ name: cloudfiles
37
+ prerelease: false
38
+ requirement: &id002 !ruby/object:Gem::Requirement
39
+ none: false
40
+ requirements:
41
+ - - ">="
42
+ - !ruby/object:Gem::Version
43
+ hash: 3
44
+ segments:
45
+ - 0
46
+ version: "0"
47
+ type: :runtime
48
+ version_requirements: *id002
49
+ - !ruby/object:Gem::Dependency
50
+ name: net-sftp
51
+ prerelease: false
52
+ requirement: &id003 !ruby/object:Gem::Requirement
53
+ none: false
54
+ requirements:
55
+ - - ">="
56
+ - !ruby/object:Gem::Version
57
+ hash: 3
58
+ segments:
59
+ - 0
60
+ version: "0"
61
+ type: :runtime
62
+ version_requirements: *id003
63
+ - !ruby/object:Gem::Dependency
64
+ name: rspec
65
+ prerelease: false
66
+ requirement: &id004 !ruby/object:Gem::Requirement
67
+ none: false
68
+ requirements:
69
+ - - ">="
70
+ - !ruby/object:Gem::Version
71
+ hash: 3
72
+ segments:
73
+ - 0
74
+ version: "0"
75
+ type: :development
76
+ version_requirements: *id004
77
+ description: |
78
+ Astrails-Safe is a simple tool to backup databases (MySQL and PostgreSQL), Subversion repositories (with svndump) and just files.
79
+ Backups can be stored locally or remotely and can be enctypted.
80
+ Remote storage is supported on Amazon S3, Rackspace Cloud Files, or just plain SFTP.
81
+
82
+ email: we@astrails.com
83
+ executables:
84
+ - astrails-safe
85
+ extensions: []
86
+
87
+ extra_rdoc_files:
88
+ - LICENSE
89
+ - README.markdown
90
+ files:
91
+ - LICENSE
92
+ - README.markdown
93
+ - Rakefile
94
+ - bin/astrails-safe
95
+ - examples/example_helper.rb
96
+ - lib/astrails/safe.rb
97
+ - lib/astrails/safe/archive.rb
98
+ - lib/astrails/safe/backup.rb
99
+ - lib/astrails/safe/cloudfiles.rb
100
+ - lib/astrails/safe/config/builder.rb
101
+ - lib/astrails/safe/config/node.rb
102
+ - lib/astrails/safe/gpg.rb
103
+ - lib/astrails/safe/gzip.rb
104
+ - lib/astrails/safe/local.rb
105
+ - lib/astrails/safe/mysqldump.rb
106
+ - lib/astrails/safe/pgdump.rb
107
+ - lib/astrails/safe/pipe.rb
108
+ - lib/astrails/safe/s3.rb
109
+ - lib/astrails/safe/sftp.rb
110
+ - lib/astrails/safe/sink.rb
111
+ - lib/astrails/safe/source.rb
112
+ - lib/astrails/safe/stream.rb
113
+ - lib/astrails/safe/svndump.rb
114
+ - lib/astrails/safe/tmp_file.rb
115
+ - lib/extensions/mktmpdir.rb
116
+ - spec/integration/archive_integration_spec.rb
117
+ - spec/integration/cleanup_spec.rb
118
+ - spec/spec.opts
119
+ - spec/spec_helper.rb
120
+ - spec/unit/archive_spec.rb
121
+ - spec/unit/cloudfiles_spec.rb
122
+ - spec/unit/config_spec.rb
123
+ - spec/unit/gpg_spec.rb
124
+ - spec/unit/gzip_spec.rb
125
+ - spec/unit/local_spec.rb
126
+ - spec/unit/mysqldump_spec.rb
127
+ - spec/unit/pgdump_spec.rb
128
+ - spec/unit/s3_spec.rb
129
+ - spec/unit/svndump_spec.rb
130
+ - templates/script.rb
131
+ has_rdoc: true
132
+ homepage: http://blog.astrails.com/astrails-safe
133
+ licenses: []
134
+
135
+ post_install_message:
136
+ rdoc_options:
137
+ - --charset=UTF-8
138
+ require_paths:
139
+ - lib
140
+ required_ruby_version: !ruby/object:Gem::Requirement
141
+ none: false
142
+ requirements:
143
+ - - ">="
144
+ - !ruby/object:Gem::Version
145
+ hash: 3
146
+ segments:
147
+ - 0
148
+ version: "0"
149
+ required_rubygems_version: !ruby/object:Gem::Requirement
150
+ none: false
151
+ requirements:
152
+ - - ">="
153
+ - !ruby/object:Gem::Version
154
+ hash: 3
155
+ segments:
156
+ - 0
157
+ version: "0"
158
+ requirements: []
159
+
160
+ rubyforge_project:
161
+ rubygems_version: 1.3.7
162
+ signing_key:
163
+ specification_version: 3
164
+ summary: Backup filesystem and databases (MySQL and PostgreSQL) locally or to a remote server/service (with encryption)
165
+ test_files:
166
+ - spec/integration/archive_integration_spec.rb
167
+ - spec/integration/cleanup_spec.rb
168
+ - spec/spec_helper.rb
169
+ - spec/unit/archive_spec.rb
170
+ - spec/unit/cloudfiles_spec.rb
171
+ - spec/unit/config_spec.rb
172
+ - spec/unit/gpg_spec.rb
173
+ - spec/unit/gzip_spec.rb
174
+ - spec/unit/local_spec.rb
175
+ - spec/unit/mysqldump_spec.rb
176
+ - spec/unit/pgdump_spec.rb
177
+ - spec/unit/s3_spec.rb
178
+ - spec/unit/svndump_spec.rb
179
+ - examples/example_helper.rb