rmysqldump 0.0.2
Sign up to get free protection for your applications and to get access to all the features.
- data/LICENSE +24 -0
- data/bin/rmysqldump +10 -0
- data/lib/rmysqldump.rb +195 -0
- data/rmysqldump.conf +23 -0
- metadata +67 -0
data/LICENSE
ADDED
@@ -0,0 +1,24 @@
|
|
1
|
+
Copyright (c) 2009, Johan Eckerström
|
2
|
+
All rights reserved.
|
3
|
+
|
4
|
+
Redistribution and use in source and binary forms, with or without
|
5
|
+
modification, are permitted provided that the following conditions are met:
|
6
|
+
* Redistributions of source code must retain the above copyright
|
7
|
+
notice, this list of conditions and the following disclaimer.
|
8
|
+
* Redistributions in binary form must reproduce the above copyright
|
9
|
+
notice, this list of conditions and the following disclaimer in the
|
10
|
+
documentation and/or other materials provided with the distribution.
|
11
|
+
* Neither the name of the <organization> nor the
|
12
|
+
names of its contributors may be used to endorse or promote products
|
13
|
+
derived from this software without specific prior written permission.
|
14
|
+
|
15
|
+
THIS SOFTWARE IS PROVIDED BY Johan Eckerström ''AS IS'' AND ANY
|
16
|
+
EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
17
|
+
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
18
|
+
DISCLAIMED. IN NO EVENT SHALL <copyright holder> BE LIABLE FOR ANY
|
19
|
+
DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
20
|
+
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
21
|
+
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
|
22
|
+
ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
23
|
+
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
24
|
+
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
data/bin/rmysqldump
ADDED
data/lib/rmysqldump.rb
ADDED
@@ -0,0 +1,195 @@
|
|
1
|
+
# $Id: rmysqldump.rb,v 1.7 2007/11/28 11:48:22 jage Exp $
|
2
|
+
#
|
3
|
+
# Written by Johan Eckerstr�m <johan@jage.se>
|
4
|
+
#
|
5
|
+
# 2007-05-22 - Stop using regexp for owner_map \
|
6
|
+
# and improve syslog message
|
7
|
+
# 2006-12-19 - Compression for servers
|
8
|
+
# 2006-12-01 - External configuration file
|
9
|
+
# 2006-11-21 - Easier to change the user mapping regexp
|
10
|
+
# 2006-10-31 - Added syslog capabilities
|
11
|
+
# 2006-08-06 - First version
|
12
|
+
#
|
13
|
+
# Todo:
|
14
|
+
# - Add regexp capabilities for the database-specifications
|
15
|
+
# - Record elapsed time for backup
|
16
|
+
# - Check for user configuration file, i.e. ~/.rmysqldump.conf
|
17
|
+
|
18
|
+
begin
|
19
|
+
require 'fileutils'
|
20
|
+
require 'syslog'
|
21
|
+
require 'rubygems'
|
22
|
+
require 'mysql'
|
23
|
+
rescue LoadError
|
24
|
+
$stderr.puts 'Could not load required libraries'; exit 1
|
25
|
+
end
|
26
|
+
|
27
|
+
begin
|
28
|
+
load '/etc/rmysqldump.conf'
|
29
|
+
rescue LoadError
|
30
|
+
$stderr.puts 'Could not load configuration'; exit 1
|
31
|
+
end
|
32
|
+
|
33
|
+
$users = []
|
34
|
+
IO.foreach('/etc/passwd') do |line|
|
35
|
+
$users << /(^[\w]+)/.match(line).to_s.strip
|
36
|
+
end
|
37
|
+
|
38
|
+
module MySQL
|
39
|
+
class Databases
|
40
|
+
|
41
|
+
attr_reader :list
|
42
|
+
|
43
|
+
def initialize
|
44
|
+
@list = databases.collect {|i| Database.new(i) }
|
45
|
+
end
|
46
|
+
|
47
|
+
def failed
|
48
|
+
@list.select {|i| i.fail }
|
49
|
+
end
|
50
|
+
|
51
|
+
def skipped
|
52
|
+
@list.select {|i| i.skip }
|
53
|
+
end
|
54
|
+
|
55
|
+
def successes
|
56
|
+
@list.select {|i| i.success }
|
57
|
+
end
|
58
|
+
|
59
|
+
private
|
60
|
+
|
61
|
+
def databases
|
62
|
+
list = []
|
63
|
+
connection = Mysql.real_connect($server[:host],
|
64
|
+
$server[:user],
|
65
|
+
$server[:password])
|
66
|
+
result = connection.query('SHOW DATABASES')
|
67
|
+
result.each {|db| list << db.to_s }
|
68
|
+
result.free
|
69
|
+
list
|
70
|
+
rescue Mysql::Error => error
|
71
|
+
$stderr.puts error.message; exit 1
|
72
|
+
end
|
73
|
+
end
|
74
|
+
|
75
|
+
class Database
|
76
|
+
|
77
|
+
attr_reader :name, :lock, :owner, :group, :charset, :skip
|
78
|
+
attr_accessor :success
|
79
|
+
|
80
|
+
def initialize(name)
|
81
|
+
@options = $database_options[name.to_sym] ||= Hash.new
|
82
|
+
|
83
|
+
@name = name
|
84
|
+
@lock = option_for(:lock)
|
85
|
+
@owner = option_for(:owner).to_s
|
86
|
+
@group = option_for(:group).to_s
|
87
|
+
@charset = option_for(:charset).to_s
|
88
|
+
@skip = option_for(:skip)
|
89
|
+
|
90
|
+
# Would be better if the database specific owner could override this
|
91
|
+
if option_for(:map_owner) && owner = find_owner
|
92
|
+
@owner = owner
|
93
|
+
end
|
94
|
+
end
|
95
|
+
|
96
|
+
def to_s
|
97
|
+
name
|
98
|
+
end
|
99
|
+
|
100
|
+
def path
|
101
|
+
"#{$archive_dir}/#{self}.sql.gz"
|
102
|
+
end
|
103
|
+
|
104
|
+
def fail
|
105
|
+
!success && !skip
|
106
|
+
end
|
107
|
+
|
108
|
+
private
|
109
|
+
|
110
|
+
def option_for(key)
|
111
|
+
@options[key] || $global_options[key] || false
|
112
|
+
end
|
113
|
+
|
114
|
+
def find_owner
|
115
|
+
match = $users.select do |u|
|
116
|
+
@name.include?(u) && u == @name[0...u.length]
|
117
|
+
end
|
118
|
+
|
119
|
+
if match.empty?
|
120
|
+
false
|
121
|
+
else
|
122
|
+
match.to_s
|
123
|
+
end
|
124
|
+
end
|
125
|
+
end
|
126
|
+
|
127
|
+
class Dump
|
128
|
+
def initialize(databases)
|
129
|
+
@databases = databases
|
130
|
+
|
131
|
+
unless mysqldump_working?
|
132
|
+
failure("Could not execute #{$mysqldump}"); exit 1
|
133
|
+
end
|
134
|
+
|
135
|
+
unless File.directory?($archive_dir)
|
136
|
+
failure("Could not save in #{$archive_dir}"); exit 1
|
137
|
+
end
|
138
|
+
end
|
139
|
+
|
140
|
+
def execute
|
141
|
+
Syslog.open(ident='rmysqldump', facility=Syslog::LOG_DAEMON)
|
142
|
+
@databases.list.each do |database|
|
143
|
+
unless database.skip
|
144
|
+
`#{$mysqldump} #{parameters_for(database)} #{database} | #{$gzip} > #{database.path}`
|
145
|
+
failure("Could not dump #{database}") unless $?.success?
|
146
|
+
begin
|
147
|
+
FileUtils.chown database.owner, database.group, database.path
|
148
|
+
FileUtils.chmod 0660, database.path
|
149
|
+
database.success = true if $?.success?
|
150
|
+
rescue => error
|
151
|
+
failure("Could not set permissions: #{error.message}")
|
152
|
+
end
|
153
|
+
end
|
154
|
+
end
|
155
|
+
message = "#{@databases.successes.length} databases dumped successfully"
|
156
|
+
if @databases.skipped.length > 0
|
157
|
+
message += ", #{@databases.skipped.length} skipped"
|
158
|
+
end
|
159
|
+
Syslog.info(message)
|
160
|
+
|
161
|
+
# Inform about failures
|
162
|
+
if @databases.failed.length > 0
|
163
|
+
error_message = 'Failed databases:'
|
164
|
+
@databases.failed.each do |db|
|
165
|
+
error_message << " #{db},"
|
166
|
+
end
|
167
|
+
error_message.gsub!(/,$/, '.')
|
168
|
+
Syslog.err(error_message)
|
169
|
+
end
|
170
|
+
|
171
|
+
Syslog.close
|
172
|
+
end
|
173
|
+
|
174
|
+
private
|
175
|
+
|
176
|
+
def failure(message)
|
177
|
+
$stderr.puts message
|
178
|
+
Syslog.err(message) if Syslog.opened?
|
179
|
+
end
|
180
|
+
|
181
|
+
def mysqldump_working?
|
182
|
+
File.readable?($mysqldump) and File.executable?($mysqldump)
|
183
|
+
end
|
184
|
+
|
185
|
+
def parameters_for(database)
|
186
|
+
params = "--default-character-set=#{database.charset} \
|
187
|
+
--user #{$server[:user]} \
|
188
|
+
--password=#{$server[:password]} \
|
189
|
+
--host #{$server[:host]}"
|
190
|
+
params += " --compress" if $server[:compress]
|
191
|
+
params += " --lock-tables" if database.lock
|
192
|
+
params
|
193
|
+
end
|
194
|
+
end
|
195
|
+
end
|
data/rmysqldump.conf
ADDED
@@ -0,0 +1,23 @@
|
|
1
|
+
$mysqldump = '/usr/local/bin/mysqldump'
|
2
|
+
$gzip = '/usr/bin/gzip'
|
3
|
+
$archive_dir = '/archive/mysqldump'
|
4
|
+
|
5
|
+
$server = {
|
6
|
+
:host => 'localhost',
|
7
|
+
:user => 'dumper',
|
8
|
+
:password => 'hemlis',
|
9
|
+
:compress => true # Compress the data stream
|
10
|
+
}
|
11
|
+
|
12
|
+
$database_options = {
|
13
|
+
:apachelogs => { :skip => true }
|
14
|
+
}
|
15
|
+
|
16
|
+
$global_options = {
|
17
|
+
:lock => false, # Lock the tables before dump
|
18
|
+
:owner => 'root', # Default user to own the backups
|
19
|
+
:group => 'wheel', # Default group to own the backups
|
20
|
+
:charset => 'latin1', # The charset to set in mysqldump
|
21
|
+
:map_owner => true # Match database name, if name starts
|
22
|
+
# a users name, he's the owner
|
23
|
+
}
|
metadata
ADDED
@@ -0,0 +1,67 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: rmysqldump
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.0.2
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- "Johan Eckerstr\xC3\xB6m"
|
8
|
+
autorequire:
|
9
|
+
bindir: bin
|
10
|
+
cert_chain: []
|
11
|
+
|
12
|
+
date: 2009-12-06 00:00:00 +01:00
|
13
|
+
default_executable: rmysqldump
|
14
|
+
dependencies:
|
15
|
+
- !ruby/object:Gem::Dependency
|
16
|
+
name: mysql
|
17
|
+
type: :runtime
|
18
|
+
version_requirement:
|
19
|
+
version_requirements: !ruby/object:Gem::Requirement
|
20
|
+
requirements:
|
21
|
+
- - ">"
|
22
|
+
- !ruby/object:Gem::Version
|
23
|
+
version: 0.0.0
|
24
|
+
version:
|
25
|
+
description: Dumping MySQL databases on the Starkast servers
|
26
|
+
email: johan@duh.se
|
27
|
+
executables:
|
28
|
+
- rmysqldump
|
29
|
+
extensions: []
|
30
|
+
|
31
|
+
extra_rdoc_files:
|
32
|
+
- LICENSE
|
33
|
+
files:
|
34
|
+
- bin/rmysqldump
|
35
|
+
- lib/rmysqldump.rb
|
36
|
+
- rmysqldump.conf
|
37
|
+
- LICENSE
|
38
|
+
has_rdoc: true
|
39
|
+
homepage: http://github.com/jage/rmysqldump
|
40
|
+
licenses: []
|
41
|
+
|
42
|
+
post_install_message:
|
43
|
+
rdoc_options:
|
44
|
+
- --charset=UTF-8
|
45
|
+
require_paths:
|
46
|
+
- lib
|
47
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
48
|
+
requirements:
|
49
|
+
- - ">="
|
50
|
+
- !ruby/object:Gem::Version
|
51
|
+
version: "0"
|
52
|
+
version:
|
53
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
54
|
+
requirements:
|
55
|
+
- - ">="
|
56
|
+
- !ruby/object:Gem::Version
|
57
|
+
version: "0"
|
58
|
+
version:
|
59
|
+
requirements: []
|
60
|
+
|
61
|
+
rubyforge_project:
|
62
|
+
rubygems_version: 1.3.5
|
63
|
+
signing_key:
|
64
|
+
specification_version: 3
|
65
|
+
summary: Dump MySQL databases
|
66
|
+
test_files: []
|
67
|
+
|