mirror of
https://github.com/viq/NewsBlur.git
synced 2025-08-05 16:49:45 +00:00
153 lines
3.9 KiB
Python
Executable file
153 lines
3.9 KiB
Python
Executable file
#!/usr/bin/env python
|
|
# -*- coding: utf-8 -*-
|
|
|
|
# Inspired by http://openquery.com/files/check_replication.pl.txt
|
|
|
|
import os
|
|
import re
|
|
|
|
import MySQLdb
|
|
|
|
from vendor.munin import MuninPlugin
|
|
|
|
|
|
class MuninMySQLPlugin(MuninPlugin):
|
|
category = "MySQL"
|
|
|
|
def __init__(self):
|
|
super(MuninMySQLPlugin, self).__init__()
|
|
|
|
self._db_master = None
|
|
self._db_slave = None
|
|
|
|
# Open a connection
|
|
def get_connection(self, source):
|
|
vars = self.getvars(source)
|
|
|
|
db = None
|
|
if source == 'master':
|
|
if not self._db_master:
|
|
self._db_master = MySQLdb.connect(**vars)
|
|
db = self._db_master
|
|
else:
|
|
if not self._db_slave:
|
|
self._db_slave = MySQLdb.connect(**vars)
|
|
db = self._db_slave
|
|
|
|
return db
|
|
|
|
# Get variables plugins
|
|
def getvars(self, source):
|
|
self.con_master = dict(
|
|
user="root",
|
|
host="localhost",
|
|
)
|
|
|
|
# Search environement vars
|
|
if source == 'master':
|
|
varname = ('m_user', 'm_passwd', 'm_host', 'm_port')
|
|
replacestr = 'm_'
|
|
else:
|
|
varname = ('s_user', 's_passwd', 's_host', 's_port')
|
|
replacestr = 's_'
|
|
|
|
conninfo = {}
|
|
for k in varname:
|
|
v = os.environ.get(k)
|
|
if v:
|
|
conninfo[k.replace(replacestr, '', 1)] = v
|
|
|
|
return conninfo
|
|
|
|
# get max bin log size
|
|
def getmaxbinlogsize(self):
|
|
db = self.get_connection('master')
|
|
c = db.cursor(MySQLdb.cursors.DictCursor)
|
|
c.execute("show variables like 'max_binlog_size'")
|
|
raw = c.fetchone()
|
|
return int(raw['Value'])
|
|
|
|
# Get replication values
|
|
def getvalues(self, source):
|
|
# get values
|
|
db = self.get_connection(source)
|
|
c = db.cursor(MySQLdb.cursors.DictCursor)
|
|
c.execute("show %(source)s status" % locals())
|
|
|
|
raw = c.fetchone()
|
|
return raw
|
|
|
|
def autoconf(self):
|
|
return bool(self.get_connection('master'))\
|
|
and bool(self.get_connection('slave'))
|
|
|
|
|
|
class MuninMySQLReplicationPlugin(MuninMySQLPlugin):
|
|
"""
|
|
|
|
from master => GRANT replication client on *.* TO munin@ip IDENTIFIED BY "password";
|
|
from slave => GRANT replication client on *.* TO munin@localhost IDENTIFIED BY "password";
|
|
|
|
ex: /etc/munin/plugin-conf.d/mysql_replication
|
|
|
|
[mysql_replication]
|
|
env.m_host x.x.x.x
|
|
env.m_user munin
|
|
env.m_passwd mysqlpass
|
|
|
|
env.s_host localhost
|
|
env.s_user munin
|
|
env.s_passwd mysqlpass
|
|
|
|
"""
|
|
|
|
args = "-l 0 --base 1000"
|
|
vlabel = "delta"
|
|
info = "Show delta position from master and slave mySQL database"
|
|
fields = (
|
|
('delta', dict(
|
|
label="Delta from master",
|
|
info="Delta not replicated from master",
|
|
type="GAUGE",
|
|
draw="AREA",
|
|
)),
|
|
)
|
|
|
|
@property
|
|
def title(self):
|
|
return "MySQL delta replication"
|
|
|
|
def execute(self):
|
|
m = self.getvalues('master')
|
|
s = self.getvalues('slave')
|
|
|
|
mfilepos = -1
|
|
sfilepos = -1
|
|
maxlogsize = self.getmaxbinlogsize()
|
|
|
|
# Search number binary file
|
|
r = re.search(r'\d+$', m['File'])
|
|
if r:
|
|
mfilepos = int(r.group(0))
|
|
r = re.search(r'\d+$', s['Relay_Master_Log_File'])
|
|
if r:
|
|
sfilepos = int(r.group(0))
|
|
|
|
mposition = int(m['Position'])
|
|
fposition = int(s['Exec_Master_Log_Pos'])
|
|
|
|
# Calc delta
|
|
deltafile = (mfilepos - sfilepos) * maxlogsize
|
|
deltaposition = mposition - fposition
|
|
delta = deltafile + deltaposition
|
|
|
|
# Close connection
|
|
self.get_connection('master').close()
|
|
self.get_connection('slave').close()
|
|
|
|
return dict(
|
|
delta=delta,
|
|
)
|
|
|
|
if __name__ == "__main__":
|
|
MuninMySQLReplicationPlugin().run()
|