小花狸監控之MySQL

壹頁書發表於2015-03-26
最近一邊學習GOLANG,一邊編寫小花狸監控.
初學這個語言,程式寫的確實太糟糕了.
不過先實現這個功能,在慢慢學習這個語言的特性.

MySQL監控內容
1.複製狀態
2.每秒網路收發情況
3.每秒增刪改查情況
4.執行緒,連線情況

該檔案引用的Host檔案沒有變化
http://blog.itpub.net/29254281/viewspace-1470440/

$GOLANG/src/probe/module/MySQL.go
package module

import (
    "database/sql"
    _ "github.com/go-sql-driver/mysql"
    "log"
    "reflect"
    "strconv"
    "strings"
    "time"
)

func GetSlaveInfo(user string, pwd string, port string) *MySQLInfo {
    mysqlinfo := &MySQLInfo{}
    NewHost(&mysqlinfo.Host)
    db, err := sql.Open("mysql", user+":"+pwd+"@tcp(127.0.0.1:"+port+")/information_schema?charset=utf8")

    if err = db.Ping(); err != nil {
        log.Fatalf("Fail to connect to mysql: %v\n", err)
    }
    defer db.Close()

    ref := reflect.ValueOf(mysqlinfo)

    rows, err := db.Query("SHOW SLAVE STATUS")
    defer rows.Close()
    if err != nil {
        log.Fatalf("Query fail: %v\n", err)
    }

    cols, _ := rows.Columns()
    buff := make([]interface{}, len(cols)) // 臨時slice
    data := make([]string, len(cols))      // 存資料slice
    for i, _ := range buff {
        buff[i] = &data[i]
    }

    for rows.Next() {
        rows.Scan(buff...) // ...是必須的
    }

    for k, col := range data {
        field := ref.Elem().FieldByName(cols[k])
        if field.IsValid() {
            switch field.Kind() {
            case reflect.Int64:
                val, _ := strconv.ParseInt(strings.Trim(col, " "), 10, 64)
                field.SetInt(val)
            case reflect.String:
                field.SetString(col)
            }
        }
    }

    cur_status, _ := db.Query("SELECT * FROM GLOBAL_STATUS")
    defer cur_status.Close()
    var name string
    var value string
    for cur_status.Next() {
        cur_status.Scan(&name, &value)
        field := ref.Elem().FieldByName(strings.Title(strings.ToLower(name)))
        if field.IsValid() {
            switch field.Kind() {
            case reflect.Int64:
                log.Println(name, "=", value)
                val, _ := strconv.ParseInt(value, 10, 64)
                field.SetInt(val)
            case reflect.String:
                field.SetString(value)
            }
        }
    }

    time.Sleep(10 * time.Second)

    cur_status_two, _ := db.Query("SELECT * FROM GLOBAL_STATUS")
    defer cur_status_two.Close()
    for cur_status_two.Next() {
        cur_status_two.Scan(&name, &value)
        field := ref.Elem().FieldByName(strings.Title(strings.ToLower(name)))
        if field.IsValid() {
            switch field.Kind() {
            case reflect.Int64:
                if !strings.HasPrefix(name, "THREAD") {
                    log.Println(name, "=", value)
                    val, _ := strconv.ParseInt(value, 10, 64)
                    field.SetInt((val - field.Int()) / 10)
                }
            }
        }
    }
    return mysqlinfo
}

type MySQLInfo struct {
    Bytes_received          int64
    Bytes_sent              int64
    Com_commit              int64
    Com_delete              int64
    Com_select              int64
    Com_rollback            int64
    Com_update              int64
    Com_insert              int64
    Com_execute_sql         int64
    Created_tmp_disk_tables int64
    Slow_queries            int64
    Slave_running           string
    Threads_connected       int64
    Threads_running         int64
    Master_Host             string
    Master_Log_File         string
    Read_Master_Log_Pos     int64
    Exec_Master_Log_Pos     int64
    Slave_IO_Running        string
    Slave_SQL_Running       string
    Seconds_Behind_Master   int64
    Host                    Host
}

呼叫
$GOLANG/scr/main.go

package main

import (
    "encoding/json"
    "log"
    "probe/module"
)

func main() {
    mysqlinfo := module.GetSlaveInfo("root", "root", "3306")
    result, _ := json.Marshal(*mysqlinfo)
    log.Println(string(result))
}

結果
{
    "Bytes_received": 265675, 
    "Bytes_sent": 1530435, 
    "Com_commit": 0, 
    "Com_delete": 0, 
    "Com_select": 835, 
    "Com_rollback": 0, 
    "Com_update": 106, 
    "Com_insert": 224, 
    "Com_execute_sql": 0, 
    "Created_tmp_disk_tables": 0, 
    "Slow_queries": 0, 
    "Slave_running": "OFF", 
    "Threads_connected": 127, 
    "Threads_running": 3, 
    "Master_Host": "", 
    "Master_Log_File": "", 
    "Read_Master_Log_Pos": 0, 
    "Exec_Master_Log_Pos": 0, 
    "Slave_IO_Running": "", 
    "Slave_SQL_Running": "", 
    "Seconds_Behind_Master": 0, 
    "Host": {
        "Ip": "172.16.1.78", 
        "Root": {
            "Name": "/", 
            "All": 50519138304, 
            "Used": 6752518144, 
            "Free": 41200336896
        }, 
        "Data": {
            "Name": "/data", 
            "All": 50519138304, 
            "Used": 6752518144, 
            "Free": 41200336896
        }, 
        "Dbdata": {
            "Name": "/dbdata", 
            "All": 0, 
            "Used": 0, 
            "Free": 0
        }, 
        "AllMemory": 7871, 
        "UsedMemory": 940, 
        "FreeMemory": 6931, 
        "CpuIdle": 99.9, 
        "Ts": "2015-03-26T20:12:45.134440733+08:00"
    }
}


參考:

來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/29254281/viewspace-1475034/,如需轉載,請註明出處,否則將追究法律責任。

相關文章