Class: EY::Backup::MysqlEngine

Inherits:
Engine show all
Defined in:
lib/ey_backup/engines/mysql_engine.rb

Constant Summary

Constants included from Spawner

Spawner::CHUNK_SIZE

Instance Attribute Summary

Attributes inherited from Engine

#allow_concurrent, #force, #host, #key_id, #log_coordinates, #password, #skip_analyze, #username

Instance Method Summary collapse

Methods inherited from Engine

#backup_running?, #block_concurrent, descendants, #gpg?, inherited, #initialize, label, lookup, register

Methods included from Spawner

#ioify, #run, #runs?, #spawn

Methods inherited from Base

#logger

Constructor Details

This class inherits a constructor from EY::Backup::Engine

Instance Method Details

#check_if_replicaObject



46
47
48
49
50
51
52
53
# File 'lib/ey_backup/engines/mysql_engine.rb', line 46

def check_if_replica
  err_msg="ERROR: Target host: '#{host}' is currently: "
  err_msg=err_msg + "a replica based on 'show slave status', " if db_replicating?
  err_msg=err_msg + "in read_only mode, " if read_only_on?
  err_msg=err_msg + "restores should be processed against the master."
  
  EY::Backup.logger.fatal(%Q{#{err_msg}}) if db_replicating? or read_only_on?
end

#cycle_database(database_name) ⇒ Object



107
108
109
110
111
112
113
114
115
# File 'lib/ey_backup/engines/mysql_engine.rb', line 107

def cycle_database(database_name)
  query = "show create database #{database_name} \\G"
  create_cmd = %x(mysql #{username_option} #{host_option} -NB -e "#{query}"|tail -n 1)
  create_cmd="Create database #{database_name}" if create_cmd==""
  
  %x(mysql #{username_option} #{host_option} -e 'DROP DATABASE IF EXISTS #{database_name}')
  %x(mysql #{username_option} #{host_option} -e '#{create_cmd}')
  
end

#databases_option(db) ⇒ Object



70
71
72
# File 'lib/ey_backup/engines/mysql_engine.rb', line 70

def databases_option(db)
  "#{db}"
end

#db_has_myisam?(database_name) ⇒ Boolean

Returns:

  • (Boolean)


86
87
88
89
90
# File 'lib/ey_backup/engines/mysql_engine.rb', line 86

def db_has_myisam?(database_name)
  query = "SELECT 1 FROM information_schema.tables WHERE table_schema='#{database_name}' AND engine='MyISAM' LIMIT 1;"
  stdout = %x{mysql #{username_option} #{host_option} -N -e"#{query}"}
  stdout.strip == '1'
end

#db_replicating?Boolean

Returns:

  • (Boolean)


92
93
94
95
# File 'lib/ey_backup/engines/mysql_engine.rb', line 92

def db_replicating?
  stdout = %x{mysql #{username_option} #{host_option} -BN -e"show slave status"|wc -l}
  stdout.to_i > 0
end

#dump(database_name, basename) ⇒ Object



6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
# File 'lib/ey_backup/engines/mysql_engine.rb', line 6

def dump(database_name, basename)
  file = basename + '.sql'

  command = "( #{server_id} mysqldump #{username_option} #{host_option} #{single_transaction_option(database_name)} #{routines_option} #{master_data_option} #{databases_option(database_name)} ) "

  if gpg?
    command << " | " << GPGEncryptor.command_for(key_id)
    file << GPGEncryptor.extension
  else
    command << " | " << GZipper.gzip
    file << GZipper.extension
  end

  command << " > #{file}"
  
  block_concurrent(database_name) unless allow_concurrent

  run(command, database_name)

  file
end

#host_optionObject



74
75
76
# File 'lib/ey_backup/engines/mysql_engine.rb', line 74

def host_option
  "-h#{host}"
end

#load(database_name, file) ⇒ Object



28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
# File 'lib/ey_backup/engines/mysql_engine.rb', line 28

def load(database_name, file)
  command = "cat #{file}"

  if file =~ /.gpz$/ # GPG?
    abort "\nCannot restore a GPG backup directly; decrypt the file (#{file}) using your key and then load using the mysql client.
  To decrypt a backup: https://support.cloud.engineyard.com/hc/en-us/articles/205413948-Use-PGP-Encrypted-Database-Backups-with-Engine-Yard-Cloud#restore
  Once decrypted, restore with: `gunzip -f < <filename> | mysql #{username_option} #{host_option} #{database_name}`\n\n"
  else
    command << " | " << GZipper.gunzip
  end
  
  cycle_database(database_name)

  command << " | mysql #{username_option} #{host_option} #{database_name} "

  run(command, database_name)
end

#log_bin_on?Boolean

Returns:

  • (Boolean)


102
103
104
105
# File 'lib/ey_backup/engines/mysql_engine.rb', line 102

def log_bin_on?
  stdout = %x{mysql #{username_option} #{host_option} -BN -e"select @@global.log_bin"}
  stdout.to_i == 1
end

#master_data_optionObject



66
67
68
# File 'lib/ey_backup/engines/mysql_engine.rb', line 66

def master_data_option
  "--master-data=2" if log_bin_on? and log_coordinates
end

#read_only_on?Boolean

Returns:

  • (Boolean)


97
98
99
100
# File 'lib/ey_backup/engines/mysql_engine.rb', line 97

def read_only_on?
  stdout = %x{mysql #{username_option} #{host_option} -BN -e"select @@global.read_only"}
  stdout.to_i == 1
end

#routines_optionObject



55
56
57
# File 'lib/ey_backup/engines/mysql_engine.rb', line 55

def routines_option
  "--routines"
end

#server_idObject



59
60
61
62
63
64
# File 'lib/ey_backup/engines/mysql_engine.rb', line 59

def server_id
  if log_bin_on? and log_coordinates
    stdout = %x{mysql #{username_option} #{host_option} -BN -e"select @@global.server_id"}
    "echo '-- Server_id: #{stdout.strip}' && "
  end 
end

#single_transaction_option(database_name) ⇒ Object



82
83
84
# File 'lib/ey_backup/engines/mysql_engine.rb', line 82

def single_transaction_option(database_name)
  '--single-transaction' unless db_has_myisam?(database_name)
end

#suffixObject



117
118
119
# File 'lib/ey_backup/engines/mysql_engine.rb', line 117

def suffix
  /sql\.(gz|gpz)$/
end

#username_optionObject



78
79
80
# File 'lib/ey_backup/engines/mysql_engine.rb', line 78

def username_option
  "-u#{username}"
end