This repository has been archived by the owner on Dec 6, 2022. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 29
/
split-mysql-dump.rb
executable file
·120 lines (100 loc) · 3.01 KB
/
split-mysql-dump.rb
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
#!/usr/bin/env ruby
require 'optparse'
tables = []
ignore = []
use_database = nil
dumpfile = ""
cmds = OptionParser.new do |opts|
opts.banner = "Usage: split-mysql-dump.rb [options] [FILE]"
opts.on("-s", "Read from stdin") do
dumpfile = $stdin
end
opts.on("-t", '--tables TABLES', Array, "Extract only these tables") do |t|
tables = t
end
opts.on("-i", '--ignore-tables TABLES', Array, "Ignore these tables") do |i|
ignore = i
end
opts.on("-u", '--use-database NAME', String, "Assume NAME as database name") do |n|
use_database = n
end
opts.on_tail("-h", "--help") do
puts opts
end
end.parse!
if dumpfile == ""
dumpfile = ARGV.shift
if not dumpfile
puts "Nothing to do"
exit
end
end
STDOUT.sync = true
class Numeric
def bytes_to_human
units = %w{B KB MB GB TB}
e = self > 0 ? (Math.log(self)/Math.log(1024)).floor : 0
s = "%.3f" % (to_f / 1024**e)
s.sub(/\.?0*$/, units[e])
end
end
if File.exist?(dumpfile)
if dumpfile == $stdin
d = $stdin
else
d = File.new(dumpfile, "r:binary")
end
outfile = nil
table = nil
db = use_database
linecount = tablecount = starttime = 0
while (line = d.gets)
# Detect table changes
if line =~ /^-- Table structure for table .(.+)./ or line =~ /^-- Dumping data for table .(.+)./ or line =~ /^# Dump of table.(.+)/
is_new_table = table != $1
table = $1
# previous file should be closed
if is_new_table
outfile.close if outfile and !outfile.closed?
puts("\n\nFound a new table: #{table}")
if (tables != [] and not tables.include?(table))
puts"`#{table}` not in list, ignoring"
table = nil
elsif (ignore != [] and ignore.include?(table))
puts"`#{table}` will be ignored"
table = nil
else
starttime = Time.now
linecount = 0
tablecount += 1
path = (db.to_s == "" ? "" : "#{db}/") + "tables";
Dir.mkdir(path) unless File.exists?(path)
outfile = File.new("#{path}/#{table}.sql", "w")
outfile.syswrite("USE `#{db}`;\n\n")
end
end
elsif line =~ /^-- Current Database: .(.+)./
db = $1
table = nil
outfile.close if outfile and !outfile.closed?
Dir.mkdir(db)
Dir.mkdir("#{db}/tables")
outfile = File.new("#{db}/create.sql", "w")
puts("\n\nFound a new db: #{db}")
elsif line =~ /^-- Position to start replication or point-in-time recovery from/
db = nil
table = nil
outfile.close if outfile and !outfile.closed?
outfile = File.new("1replication.sql", "w")
puts("\n\nFound replication data")
end
# Write line to outfile
if outfile and !outfile.closed?
outfile.syswrite(line)
linecount += 1
elapsed = Time.now.to_i - starttime.to_i + 1
print(" writing line: #{linecount} #{outfile.stat.size.bytes_to_human} in #{elapsed} seconds #{(outfile.stat.size / elapsed).bytes_to_human}/sec \r")
end
end
end
puts