namxam-backup 2.4.5

Sign up to get free protection for your applications and to get access to all the features.
Files changed (61) hide show
  1. data/CHANGELOG +131 -0
  2. data/LICENSE +20 -0
  3. data/README.md +122 -0
  4. data/bin/backup +108 -0
  5. data/generators/backup/backup_generator.rb +69 -0
  6. data/generators/backup/templates/backup.rake +56 -0
  7. data/generators/backup/templates/backup.rb +253 -0
  8. data/generators/backup/templates/create_backup_tables.rb +18 -0
  9. data/generators/backup_update/backup_update_generator.rb +50 -0
  10. data/generators/backup_update/templates/migrations/update_backup_tables.rb +27 -0
  11. data/lib/backup.rb +132 -0
  12. data/lib/backup/adapters/archive.rb +34 -0
  13. data/lib/backup/adapters/base.rb +167 -0
  14. data/lib/backup/adapters/custom.rb +41 -0
  15. data/lib/backup/adapters/mongo_db.rb +139 -0
  16. data/lib/backup/adapters/mysql.rb +60 -0
  17. data/lib/backup/adapters/postgresql.rb +56 -0
  18. data/lib/backup/adapters/sqlite.rb +25 -0
  19. data/lib/backup/command_helper.rb +14 -0
  20. data/lib/backup/configuration/adapter.rb +21 -0
  21. data/lib/backup/configuration/adapter_options.rb +8 -0
  22. data/lib/backup/configuration/attributes.rb +19 -0
  23. data/lib/backup/configuration/base.rb +75 -0
  24. data/lib/backup/configuration/helpers.rb +24 -0
  25. data/lib/backup/configuration/mail.rb +20 -0
  26. data/lib/backup/configuration/smtp.rb +8 -0
  27. data/lib/backup/configuration/storage.rb +8 -0
  28. data/lib/backup/connection/cloudfiles.rb +75 -0
  29. data/lib/backup/connection/dropbox.rb +62 -0
  30. data/lib/backup/connection/s3.rb +88 -0
  31. data/lib/backup/core_ext/object.rb +5 -0
  32. data/lib/backup/environment/base.rb +12 -0
  33. data/lib/backup/environment/rails_configuration.rb +15 -0
  34. data/lib/backup/environment/unix_configuration.rb +109 -0
  35. data/lib/backup/mail/base.rb +97 -0
  36. data/lib/backup/mail/mail.txt +7 -0
  37. data/lib/backup/record/base.rb +65 -0
  38. data/lib/backup/record/cloudfiles.rb +28 -0
  39. data/lib/backup/record/dropbox.rb +27 -0
  40. data/lib/backup/record/ftp.rb +39 -0
  41. data/lib/backup/record/local.rb +26 -0
  42. data/lib/backup/record/s3.rb +25 -0
  43. data/lib/backup/record/scp.rb +33 -0
  44. data/lib/backup/record/sftp.rb +38 -0
  45. data/lib/backup/storage/base.rb +10 -0
  46. data/lib/backup/storage/cloudfiles.rb +16 -0
  47. data/lib/backup/storage/dropbox.rb +12 -0
  48. data/lib/backup/storage/ftp.rb +38 -0
  49. data/lib/backup/storage/local.rb +22 -0
  50. data/lib/backup/storage/s3.rb +15 -0
  51. data/lib/backup/storage/scp.rb +30 -0
  52. data/lib/backup/storage/sftp.rb +31 -0
  53. data/lib/backup/version.rb +3 -0
  54. data/lib/generators/backup/USAGE +10 -0
  55. data/lib/generators/backup/backup_generator.rb +47 -0
  56. data/lib/generators/backup/templates/backup.rake +56 -0
  57. data/lib/generators/backup/templates/backup.rb +236 -0
  58. data/lib/generators/backup/templates/create_backup_tables.rb +18 -0
  59. data/setup/backup.rb +255 -0
  60. data/setup/backup.sqlite3 +0 -0
  61. metadata +278 -0
@@ -0,0 +1,33 @@
1
+ require 'net/scp'
2
+
3
+ module Backup
4
+ module Record
5
+ class SCP < Backup::Record::Base
6
+
7
+ attr_accessor :ip, :user, :password
8
+
9
+ def load_specific_settings(adapter)
10
+ %w(ip user password path).each do |method|
11
+ send(:"#{method}=", adapter.procedure.get_storage_configuration.attributes[method])
12
+ end
13
+ end
14
+
15
+ private
16
+
17
+ def self.destroy_backups(procedure, backups)
18
+ ip = procedure.get_storage_configuration.attributes['ip']
19
+ user = procedure.get_storage_configuration.attributes['user']
20
+ password = procedure.get_storage_configuration.attributes['password']
21
+
22
+ Net::SSH.start(ip, user, :password => password) do |ssh|
23
+ backups.each do |backup|
24
+ puts "\nDestroying backup \"#{backup.filename}\" from path \"#{backup.path}\"."
25
+ ssh.exec("rm #{File.join(backup.path, backup.filename)}")
26
+ backup.destroy
27
+ end
28
+ end
29
+ end
30
+
31
+ end
32
+ end
33
+ end
@@ -0,0 +1,38 @@
1
+ require 'net/sftp'
2
+
3
+ module Backup
4
+ module Record
5
+ class SFTP < Backup::Record::Base
6
+
7
+ attr_accessor :ip, :user, :password
8
+
9
+ def load_specific_settings(adapter)
10
+ %w(ip user password path).each do |method|
11
+ send(:"#{method}=", adapter.procedure.get_storage_configuration.attributes[method])
12
+ end
13
+ end
14
+
15
+ private
16
+
17
+ def self.destroy_backups(procedure, backups)
18
+ ip = procedure.get_storage_configuration.attributes['ip']
19
+ user = procedure.get_storage_configuration.attributes['user']
20
+ password = procedure.get_storage_configuration.attributes['password']
21
+
22
+ Net::SFTP.start(ip, user, :password => password) do |sftp|
23
+ backups.each do |backup|
24
+ puts "\nDestroying backup \"#{backup.filename}\" from path \"#{backup.path}\"."
25
+ begin
26
+ sftp.remove!(File.join(backup.path, backup.filename))
27
+ backup.destroy
28
+ rescue
29
+ puts "Could not find backup #{backup.path}/#{backup.filename}.."
30
+ backup.destroy
31
+ end
32
+ end
33
+ end
34
+ end
35
+
36
+ end
37
+ end
38
+ end
@@ -0,0 +1,10 @@
1
+ module Backup
2
+ module Storage
3
+ class Base
4
+ include Backup::CommandHelper
5
+
6
+ end
7
+ end
8
+ end
9
+
10
+
@@ -0,0 +1,16 @@
1
+ require 'backup/connection/cloudfiles'
2
+
3
+ module Backup
4
+ module Storage
5
+ class CloudFiles < Base
6
+
7
+ # Stores the backup file on the remote server using Rackspace Cloud Files
8
+ def initialize(adapter)
9
+ cf = Backup::Connection::CloudFiles.new(adapter)
10
+ cf.connect
11
+ cf.store
12
+ end
13
+
14
+ end
15
+ end
16
+ end
@@ -0,0 +1,12 @@
1
+ require 'backup/connection/dropbox'
2
+
3
+ module Backup
4
+ module Storage
5
+ class Dropbox < Base
6
+ def initialize(adapter)
7
+ dropbox = Backup::Connection::Dropbox.new(adapter)
8
+ dropbox.store
9
+ end
10
+ end
11
+ end
12
+ end
@@ -0,0 +1,38 @@
1
+ require 'net/ftp'
2
+
3
+ module Backup
4
+ module Storage
5
+ class FTP < Backup::Storage::Base
6
+
7
+ attr_accessor :user, :password, :ip, :path, :tmp_path, :final_file
8
+
9
+ # Stores the backup file on the remote server using FTP
10
+ def initialize(adapter)
11
+ %w(ip user password path).each do |method|
12
+ send("#{method}=", adapter.procedure.get_storage_configuration.attributes[method])
13
+ end
14
+
15
+ final_file = adapter.final_file
16
+ tmp_path = adapter.tmp_path
17
+
18
+ Net::FTP.open(ip, user, password) do |ftp|
19
+ begin
20
+ ftp.chdir(path)
21
+ rescue
22
+ puts "Could not find or access \"#{path}\" on \"#{ip}\", please ensure this directory exists and is accessible by the user \"#{user}\"."
23
+ exit
24
+ end
25
+
26
+ begin
27
+ puts "Storing \"#{final_file}\" to path \"#{path}\" on remote server (#{ip})."
28
+ ftp.putbinaryfile(File.join(tmp_path, final_file).gsub('\ ', ' '), File.join(path, final_file))
29
+ rescue
30
+ puts "Could not save file to backup server. Is the \"#{path}\" directory writable?"
31
+ exit
32
+ end
33
+ end
34
+ end
35
+
36
+ end
37
+ end
38
+ end
@@ -0,0 +1,22 @@
1
+ module Backup
2
+ module Storage
3
+ class Local < Base
4
+
5
+ # Store on same machine, preferentially in a different hard drive or in
6
+ # a mounted network path (NFS, Samba, etc)
7
+ attr_accessor :path, :tmp_path, :final_file
8
+
9
+ # Stores the backup file on local machine
10
+ def initialize(adapter)
11
+ self.path = adapter.procedure.get_storage_configuration.attributes['path']
12
+ self.tmp_path = adapter.tmp_path
13
+ self.final_file = adapter.final_file
14
+
15
+ run "mkdir -p #{path}"
16
+ run "cp #{File.join(tmp_path, final_file).gsub('\ ', ' ')} #{File.join(path, final_file)}"
17
+ end
18
+
19
+ end
20
+ end
21
+ end
22
+
@@ -0,0 +1,15 @@
1
+ require 'backup/connection/s3'
2
+
3
+ module Backup
4
+ module Storage
5
+ class S3 < Base
6
+
7
+ # Stores the backup file on the remote server using S3
8
+ def initialize(adapter)
9
+ s3 = Backup::Connection::S3.new(adapter)
10
+ s3.store
11
+ end
12
+
13
+ end
14
+ end
15
+ end
@@ -0,0 +1,30 @@
1
+ require 'net/scp'
2
+
3
+ module Backup
4
+ module Storage
5
+ class SCP < Base
6
+
7
+ attr_accessor :user, :password, :ip, :path, :tmp_path, :final_file
8
+
9
+ # Stores the backup file on the remote server using SCP
10
+ def initialize(adapter)
11
+ %w(ip user password path).each do |method|
12
+ send("#{method}=", adapter.procedure.get_storage_configuration.attributes[method])
13
+ end
14
+
15
+ final_file = adapter.final_file
16
+ tmp_path = adapter.tmp_path
17
+
18
+ Net::SSH.start(ip, user, :password => password) do |ssh|
19
+ ssh.exec "mkdir -p #{path}"
20
+ end
21
+
22
+ puts "Storing \"#{final_file}\" to path \"#{path}\" on remote server (#{ip})."
23
+ Net::SCP.start(ip, user, :password => password) do |scp|
24
+ scp.upload! File.join(tmp_path, final_file).gsub('\ ', ' '), path
25
+ end
26
+ end
27
+
28
+ end
29
+ end
30
+ end
@@ -0,0 +1,31 @@
1
+ require 'net/sftp'
2
+
3
+ module Backup
4
+ module Storage
5
+ class SFTP < Base
6
+
7
+ attr_accessor :user, :password, :ip, :path, :tmp_path, :final_file
8
+
9
+ # Stores the backup file on the remote server using SFTP
10
+ def initialize(adapter)
11
+ %w(ip user password path).each do |method|
12
+ send("#{method}=", adapter.procedure.get_storage_configuration.attributes[method])
13
+ end
14
+
15
+ final_file = adapter.final_file
16
+ tmp_path = adapter.tmp_path
17
+
18
+ Net::SFTP.start(ip, user, :password => password) do |sftp|
19
+ begin
20
+ puts "Storing \"#{final_file}\" to path \"#{path}\" on remote server (#{ip})."
21
+ sftp.upload!(File.join(tmp_path, final_file).gsub('\ ', ' '), File.join(path, final_file))
22
+ rescue
23
+ puts "Could not find \"#{path}\" on \"#{ip}\", please ensure this directory exists."
24
+ exit
25
+ end
26
+ end
27
+ end
28
+
29
+ end
30
+ end
31
+ end
@@ -0,0 +1,3 @@
1
+ module Backup
2
+ VERSION = "2.4.5"
3
+ end
@@ -0,0 +1,10 @@
1
+ Description:
2
+ Backup's Ruby on Rails 3 Generator
3
+
4
+ Example:
5
+ rails generate backup
6
+
7
+ This will create:
8
+ * lib/tasks/backup.rake
9
+ * config/backup.rb
10
+ * db/migrate/<DateTime>_create_backup_tables.rb
@@ -0,0 +1,47 @@
1
+ class BackupGenerator < Rails::Generators::Base
2
+ source_root File.expand_path('../templates', __FILE__)
3
+
4
+ def copy_files
5
+ copy_file 'backup.rake', 'lib/tasks/backup.rake'
6
+ copy_file 'backup.rb', 'config/backup.rb'
7
+
8
+ unless Dir["#{Rails.root}/db/migrate/*create_backup_tables.rb"].any?
9
+ copy_file 'create_backup_tables.rb', "db/migrate/#{Time.now.utc.strftime("%Y%m%d%H%M%S")}_create_backup_tables.rb"
10
+ end
11
+
12
+ puts message
13
+ end
14
+
15
+ def message
16
+ <<-MESSAGE
17
+
18
+
19
+ ==============================================================
20
+ Backup's files have been generated!
21
+ ==============================================================
22
+
23
+ 1: Migrate the database!
24
+
25
+ rake db:migrate
26
+
27
+
28
+ 2: Set up some "Backup Settings" inside the backup configuration file!
29
+
30
+ config/backup.rb
31
+
32
+
33
+ 3: Run the backups! Enjoy.
34
+
35
+ rake backup:run trigger="your-specified-trigger"
36
+
37
+
38
+ For More Information:
39
+ http://github.com/meskyanichi/backup
40
+
41
+ ==============================================================
42
+
43
+
44
+ MESSAGE
45
+ end
46
+
47
+ end
@@ -0,0 +1,56 @@
1
+ namespace :backup do
2
+
3
+ task :boot => :environment do
4
+ Backup::System.boot!
5
+ end
6
+
7
+ desc "Run Backup Procedure."
8
+ task :run => :boot do
9
+ puts "Running: #{ENV['trigger']}."
10
+ Backup::Setup.new(ENV['trigger'], @backup_procedures).initialize_adapter
11
+ end
12
+
13
+ desc "Finds backup records by trigger"
14
+ task :find => :boot do
15
+ puts "Finding backup records with trigger: #{ENV['trigger']}."
16
+ backup = Backup::Setup.new(ENV['trigger'], @backup_procedures)
17
+ records = backup.procedure.record_class.all( :conditions => {:trigger => ENV['trigger']} )
18
+
19
+ if ENV['table'].eql?("true")
20
+ puts Hirb::Helpers::AutoTable.render(records)
21
+ else
22
+ records.each do |record|
23
+ puts record.to_yaml
24
+ end
25
+ end
26
+ end
27
+
28
+ desc "Truncates all records for the specified \"trigger\", excluding the physical files on s3 or the remote server."
29
+ task :truncate => :boot do
30
+ puts "Truncating backup records with trigger: #{ENV['trigger']}."
31
+ Backup::Record::Base.destroy_all :trigger => ENV['trigger']
32
+ end
33
+
34
+ desc "Truncates everything."
35
+ task :truncate_all => :boot do
36
+ puts "Truncating all backup records."
37
+ Backup::Record::Base.destroy_all
38
+ end
39
+
40
+ desc "Destroys all records for the specified \"trigger\", including the physical files on s3 or the remote server."
41
+ task :destroy => :boot do
42
+ puts "Destroying backup records with trigger: #{ENV['trigger']}."
43
+ backup = Backup::Setup.new(ENV['trigger'], @backup_procedures)
44
+ backup.procedure.record_class.destroy_all_backups( backup.procedure, ENV['trigger'] )
45
+ end
46
+
47
+ desc "Destroys all records for the specified \"trigger\", including the physical files on s3 or the remote server."
48
+ task :destroy_all => :boot do
49
+ puts "Destroying all backup records."
50
+ backup = Backup::Setup.new(false, @backup_procedures)
51
+ backup.procedures.each do |backup_procedure|
52
+ backup_procedure.record_class.destroy_all_backups( backup_procedure, backup_procedure.trigger )
53
+ end
54
+ end
55
+
56
+ end
@@ -0,0 +1,236 @@
1
+ # Backup Configuration File
2
+ #
3
+ # Use the "backup" block to add backup settings to the configuration file.
4
+ # The argument before the "do" in (backup "argument" do) is called a "trigger".
5
+ # This acts as the identifier for the configuration.
6
+ #
7
+ # In the example below we have a "mysql-backup-s3" trigger for the backup setting.
8
+ # All the configuration is done inside this block. To initialize the backup process for this block,
9
+ # you invoke it using the following rake task:
10
+ #
11
+ # rake backup:run trigger="mysql-backup-s3"
12
+ #
13
+ # You can add as many backup block settings as you want, just be sure every trigger is unique and you can run
14
+ # each of them separately.
15
+ #
16
+ # ADAPTERS
17
+ # - MySQL
18
+ # - PostgreSQL
19
+ # - SQLite
20
+ # - MongoDB
21
+ # - Archive
22
+ # - Custom
23
+ #
24
+ # STORAGE METHODS
25
+ # - S3 (Amazon)
26
+ # - CF (Rackspace Cloud Files)
27
+ # - SCP (Remote Server)
28
+ # - FTP (Remote Server)
29
+ # - SFTP (Remote Server)
30
+ # - LOCAL (Local Server)
31
+ #
32
+ # GLOBAL OPTIONS
33
+ # - Keep Backups (keep_backups)
34
+ # - Encrypt With Pasword (encrypt_with_password)
35
+ # - Encrypt With GPG Public Key (encrypt_with_gpg_public_key)
36
+ # - Notify (notify)
37
+ #
38
+ # This is the "decrypt" command for all encrypted backups:
39
+ # sudo backup --decrypt /path/to/encrypted/file
40
+ #
41
+ # Each Backup Setting can contain:
42
+ # - 1 Adapter
43
+ # - 1 Storage Method
44
+ # - Multiple Global Options
45
+ #
46
+ # The combination of these, however, do not matter! So experiment with it.
47
+ #
48
+ # You can also let Backup notify you by email on successfully created backups.
49
+ # - Just uncomment the block of code below (notifier_settings) and fill in your credentials.
50
+ # - Then for set "notify" to "true" in each (backup) block you wish to be notified of.
51
+ #
52
+ # For more information on "Backup", please refer to the wiki on github
53
+ # http://wiki.github.com/meskyanichi/backup/configuration-file
54
+
55
+
56
+ # Notifier
57
+ # Uncomment this if you want to enable notification by email on successful backup runs
58
+ # You will also have to set "notify true" inside each backup block below to enable it for that particular backup
59
+ # notifier_settings do
60
+ #
61
+ # to "example1@gmail.com"
62
+ # from "example2@gmail.com"
63
+ #
64
+ # smtp do
65
+ # host "smtp.gmail.com"
66
+ # port "587"
67
+ # username "example1@gmail.com"
68
+ # password "example1password"
69
+ # authentication "plain"
70
+ # domain "localhost.localdomain"
71
+ # tls true
72
+ # end
73
+ #
74
+ # end
75
+
76
+
77
+ # Initialize with:
78
+ # rake backup:run trigger='mongo-backup-s3'
79
+ backup 'mongo-backup-s3' do
80
+
81
+ adapter :mongo do
82
+ database "your_mongo_database"
83
+ #There are two ways to backup mongo:
84
+ # * :mongodump (DEFAULT) fairly fast, non-blocking, creates smaller bson files, need to import to recover
85
+ # * :disk_copy locks the database (use a slave!!!), does a disk-level copy, and then unlocks. fast, blocking, large archives, but very fast to recover
86
+ backup_method :mongodump #default
87
+ database :my_mongo_collection
88
+ options do
89
+ # host mongo.mysite.com
90
+ # port 27018 #perhaps you have a slave instance
91
+ # username user
92
+ # password secret
93
+ end
94
+ end
95
+
96
+ storage :s3 do
97
+ access_key_id 'access_key_id'
98
+ secret_access_key 'secret_access_key'
99
+ # host 's3-ap-southeast-1.amazonaws.com' #the s3 location. Defaults to us-east-1
100
+ bucket '/bucket/backups/mysql/'
101
+ use_ssl true
102
+ end
103
+
104
+ keep_backups 25
105
+ encrypt_with_gpg_public_key <<-KEY
106
+ -----BEGIN PGP PUBLIC KEY BLOCK-----
107
+ Version: GnuPG v1.4.10 (Darwin)
108
+
109
+ public key goes here
110
+ -----END PGP PUBLIC KEY BLOCK-----
111
+ KEY
112
+ notify false
113
+ end
114
+
115
+ # Initialize with:
116
+ # rake backup:run trigger='mysql-backup-cloudfiles'
117
+ backup 'mysql-backup-cloudfiles' do
118
+
119
+ adapter :mysql do
120
+ user 'user'
121
+ password 'password'
122
+ database 'database'
123
+ end
124
+
125
+ storage :cloudfiles do
126
+ username 'username'
127
+ api_key 'api_key'
128
+ container 'mysql_backup'
129
+ end
130
+
131
+ encrypt_with_gpg_public_key <<-KEY
132
+ -----BEGIN PGP PUBLIC KEY BLOCK-----
133
+ Version: GnuPG v1.4.7 (Darwin)
134
+
135
+ Your very long public key goes here
136
+ -----END PGP PUBLIC KEY BLOCK-----
137
+ KEY
138
+
139
+ end
140
+
141
+ # Initialize with:
142
+ # rake backup:run trigger='postgresql-backup-s3'
143
+ backup 'postgresql-backup-scp' do
144
+
145
+ adapter :postgresql do
146
+ user 'user'
147
+ database 'database'
148
+
149
+ # skip_tables ['table1', 'table2', 'table3']
150
+
151
+ # options do
152
+ # host '123.45.678.90'
153
+ # port '80'
154
+ # socket '/tmp/socket.sock'
155
+ # end
156
+ # additional_options '--clean --blobs'
157
+ end
158
+
159
+ storage :scp do
160
+ ip 'example.com'
161
+ user 'user'
162
+ password 'password'
163
+ path '/var/backups/postgresql/'
164
+ end
165
+
166
+ keep_backups :all
167
+ encrypt_with_password false
168
+ notify false
169
+
170
+ end
171
+
172
+
173
+ # Initialize with:
174
+ # rake backup:run trigger='archive-backup-ftp'
175
+ backup 'archive-backup-ftp' do
176
+
177
+ adapter :archive do
178
+ files ["#{RAILS_ROOT}/log", "#{RAILS_ROOT}/db"]
179
+ end
180
+
181
+ storage :ftp do
182
+ ip 'example.com'
183
+ user 'user'
184
+ password 'password'
185
+ path '/var/backups/archive/'
186
+ end
187
+
188
+ keep_backups 10
189
+ encrypt_with_password false
190
+ notify false
191
+
192
+ end
193
+
194
+
195
+ # Initialize with:
196
+ # rake backup:run trigger='custom-backup-sftp'
197
+ backup 'custom-backup-sftp' do
198
+
199
+ adapter :custom do
200
+ commands \
201
+ [ "mysqldump [options] [database] > :tmp_path/my_mysql_dump.sql",
202
+ "pg_dump [options] [database] > :tmp_path/my_postgresql_dump.sql",
203
+ "any_other_db_format [options] [database] > :tmp_path/my_any_other_db_format.sql" ]
204
+ end
205
+
206
+ storage :sftp do
207
+ ip 'example.com'
208
+ user 'user'
209
+ password 'password'
210
+ path '/var/backups/custom/'
211
+ end
212
+
213
+ keep_backups :all
214
+ encrypt_with_password 'password'
215
+ notify false
216
+
217
+ end
218
+
219
+
220
+ # Initializ with:
221
+ # rake backup:run trigger='sqlite-backup-local'
222
+ backup 'sqlite-backup-local' do
223
+
224
+ adapter :sqlite do
225
+ database "#{RAILS_ROOT}/db/production.sqlite3"
226
+ end
227
+
228
+ storage :local do
229
+ path "/path/to/storage/location/"
230
+ end
231
+
232
+ keep_backups :all
233
+ encrypt_with_password false
234
+ notify false
235
+
236
+ end