Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
35 changes: 26 additions & 9 deletions collector/slave_hosts.go
Original file line number Diff line number Diff line change
Expand Up @@ -80,25 +80,42 @@ func (ScrapeSlaveHosts) Scrape(ctx context.Context, db *sql.DB, ch chan<- promet
var masterId string
var slaveUuid string

columnNames, err := slaveHostsRows.Columns()
if err != nil {
return err
}

for slaveHostsRows.Next() {
// Newer versions of mysql have the following
// Server_id, Host, Port, Master_id, Slave_UUID
// Older versions of mysql have the following
// Server_id, Host, Port, Rpl_recovery_rank, Master_id
err := slaveHostsRows.Scan(&serverId, &host, &port, &rrrOrMasterId, &slaveUuidOrMasterId)
// MySQL 5.5 and MariaDB 10.5 have the following
// Server_id, Host, Port, Master_id
if len(columnNames) == 5 {
err = slaveHostsRows.Scan(&serverId, &host, &port, &rrrOrMasterId, &slaveUuidOrMasterId)
} else {
err = slaveHostsRows.Scan(&serverId, &host, &port, &rrrOrMasterId)
}
if err != nil {
return err
}

// Check to see if slaveUuidOrMasterId resembles a UUID or not
// to find out if we are using an old version of MySQL
if _, err = uuid.FromString(slaveUuidOrMasterId); err != nil {
// We are running an older version of MySQL with no slave UUID
slaveUuid = ""
masterId = slaveUuidOrMasterId
// if a Slave_UUID or Rpl_recovery_rank field is present
if len(columnNames) == 5 {
// Check to see if slaveUuidOrMasterId resembles a UUID or not
// to find out if we are using an old version of MySQL
if _, err = uuid.FromString(slaveUuidOrMasterId); err != nil {
// We are running an older version of MySQL with no slave UUID
slaveUuid = ""
masterId = slaveUuidOrMasterId
} else {
// We are running a more recent version of MySQL
slaveUuid = slaveUuidOrMasterId
masterId = rrrOrMasterId
}
} else {
// We are running a more recent version of MySQL
slaveUuid = slaveUuidOrMasterId
slaveUuid = ""
masterId = rrrOrMasterId
}

Expand Down
38 changes: 38 additions & 0 deletions collector/slave_hosts_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -99,3 +99,41 @@ func TestScrapeSlaveHostsNewFormat(t *testing.T) {
t.Errorf("there were unfulfilled exceptions: %s", err)
}
}

func TestScrapeSlaveHostsWithoutSlaveUuid(t *testing.T) {
db, mock, err := sqlmock.New()
if err != nil {
t.Fatalf("error opening a stub database connection: %s", err)
}
defer db.Close()

columns := []string{"Server_id", "Host", "Port", "Master_id"}
rows := sqlmock.NewRows(columns).
AddRow("192168010", "iconnect2", "3306", "192168012").
AddRow("1921680101", "athena", "3306", "192168012")
mock.ExpectQuery(sanitizeQuery("SHOW SLAVE HOSTS")).WillReturnRows(rows)

ch := make(chan prometheus.Metric)
go func() {
if err = (ScrapeSlaveHosts{}).Scrape(context.Background(), db, ch, log.NewNopLogger()); err != nil {
t.Errorf("error calling function on test: %s", err)
}
close(ch)
}()

counterExpected := []MetricResult{
{labels: labelMap{"server_id": "192168010", "slave_host": "iconnect2", "port": "3306", "master_id": "192168012", "slave_uuid": ""}, value: 1, metricType: dto.MetricType_GAUGE},
{labels: labelMap{"server_id": "1921680101", "slave_host": "athena", "port": "3306", "master_id": "192168012", "slave_uuid": ""}, value: 1, metricType: dto.MetricType_GAUGE},
}
convey.Convey("Metrics comparison", t, func() {
for _, expect := range counterExpected {
got := readMetric(<-ch)
convey.So(got, convey.ShouldResemble, expect)
}
})

// Ensure all SQL queries were executed
if err := mock.ExpectationsWereMet(); err != nil {
t.Errorf("there were unfulfilled exceptions: %s", err)
}
}