-
Notifications
You must be signed in to change notification settings - Fork 2
Expand file tree
/
Copy pathdump_hook.rb
More file actions
124 lines (113 loc) · 3.65 KB
/
Copy pathdump_hook.rb
File metadata and controls
124 lines (113 loc) · 3.65 KB
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
121
122
123
124
require "dump_hook/version"
require "dump_hook/hooks/mysql"
require "dump_hook/hooks/postgres"
require "timecop"
require "ostruct"
module DumpHook
class Settings
attr_accessor :database,
:dumps_location,
:remove_old_dumps,
:actual,
:database_type,
:username,
:password,
:host,
:port,
:sources,
:with_sources
def initialize
@database_type = 'postgres'
@dumps_location = 'tmp/dump_hook'
@remove_old_dumps = true
@with_sources = false
@sources = {}
end
end
class << self
attr_accessor :settings
attr_accessor :hooks
def setup
self.settings = Settings.new
yield(settings)
unless settings.sources.empty?
settings.with_sources = true
end
unless settings.database.nil?
single_source = { type: settings.database_type.to_sym,
database: settings.database,
username: settings.username,
password: settings.password,
host: settings.host,
port: settings.port }
self.settings.sources[settings.database_type.to_sym] = single_source
end
end
end
def execute_with_dump(name, opts={}, &block)
created_on = opts[:created_on]
actual = opts[:actual] || settings.actual
create_dirs_if_not_exists
filename = full_filename(name, created_on, actual)
if File.exist?(filename)
restore_dump(filename)
else
if created_on
Timecop.travel(created_on)
elsif actual && settings.remove_old_dumps
FileUtils.rm(Dir.glob(full_filename(name, nil, "*")))
end
block.call
Timecop.return
store_dump(filename)
end
end
def settings
DumpHook.settings
end
def store_dump(filename)
FileUtils.mkdir_p(filename)
settings.sources.each do |name, parameters|
filename_with_namespace = File.join(filename, "#{name}.dump")
connection_settings = OpenStruct.new(parameters.slice(:database, :username, :password, :port, :host))
dumper = case parameters[:type]
when :postgres
Hooks::Postgres.new(connection_settings)
when :mysql
Hooks::MySql.new(connection_settings)
else
raise "Unsupported type of source"
end
dumper.dump(filename_with_namespace)
end
end
def restore_dump(filename)
FileUtils.mkdir_p(filename)
settings.sources.each do |name, parameters|
filename_with_namespace = File.join(filename, "#{name}.dump")
connection_settings = OpenStruct.new(parameters.slice(:database, :username, :password, :port, :host))
dumper = case parameters[:type]
when :postgres
Hooks::Postgres.new(connection_settings)
when :mysql
Hooks::MySql.new(connection_settings)
else
raise "Unsupported type of source"
end
dumper.restore(filename_with_namespace)
end
end
def full_filename(name, created_on, actual)
name_with_created_on = name
if created_on
name_with_created_on = "#{name_with_created_on}_#{created_on.to_s(:number)}"
elsif actual
name_with_created_on = "#{name_with_created_on}_actual#{actual}"
end
full_path = "#{settings.dumps_location}/#{name_with_created_on}"
settings.with_sources ? full_path : "#{full_path}.dump"
end
def create_dirs_if_not_exists
FileUtils.mkdir_p(settings.dumps_location)
end
end