From ff0b8b9dffc65d1b003f048ac44d7bd0b185f228 Mon Sep 17 00:00:00 2001 From: Alexander Zobnin Date: Tue, 2 Jun 2020 17:18:38 +0300 Subject: [PATCH] refactor and removing unused code --- pkg/datasource.go | 132 +++++++++++----------------------------- pkg/models.go | 99 ------------------------------ pkg/zabbix.go | 6 ++ pkg/zabbixapi/models.go | 7 +++ 4 files changed, 50 insertions(+), 194 deletions(-) diff --git a/pkg/datasource.go b/pkg/datasource.go index e225f0d..2aa0dec 100644 --- a/pkg/datasource.go +++ b/pkg/datasource.go @@ -2,32 +2,19 @@ package main import ( "context" - "crypto/tls" "encoding/json" "errors" "fmt" - "net" - "net/http" - "net/url" "time" "github.com/alexanderzobnin/grafana-zabbix/pkg/gtime" "github.com/alexanderzobnin/grafana-zabbix/pkg/zabbixapi" - hclog "github.com/hashicorp/go-hclog" - plugin "github.com/hashicorp/go-plugin" "github.com/grafana/grafana-plugin-sdk-go/backend" "github.com/grafana/grafana-plugin-sdk-go/backend/log" "github.com/grafana/grafana-plugin-sdk-go/data" ) -// ZabbixPlugin implements the Grafana backend interface and forwards queries to the ZabbixDatasourceInstance -type ZabbixPlugin struct { - plugin.NetRPCUnsupportedPlugin - logger hclog.Logger - datasourceCache *Cache -} - type ZabbixDatasource struct { datasourceCache *Cache logger log.Logger @@ -36,25 +23,32 @@ type ZabbixDatasource struct { // ZabbixDatasourceInstance stores state about a specific datasource // and provides methods to make requests to the Zabbix API type ZabbixDatasourceInstance struct { - url *url.URL - authToken string zabbixAPI *zabbixapi.ZabbixAPI dsInfo *backend.DataSourceInstanceSettings Settings *ZabbixDatasourceSettings queryCache *Cache - httpClient *http.Client logger log.Logger } -// NewZabbixDatasource returns new datasource instance. -func (ds *ZabbixDatasource) NewZabbixDatasource(dsInfo *backend.DataSourceInstanceSettings) (*ZabbixDatasourceInstance, error) { - dsInstance, err := newZabbixDatasource(dsInfo) +// NewZabbixDatasourceInstance returns an initialized zabbix datasource instance +func NewZabbixDatasourceInstance(dsInfo *backend.DataSourceInstanceSettings) (*ZabbixDatasourceInstance, error) { + zabbixAPI, err := zabbixapi.New(dsInfo.URL) if err != nil { return nil, err } - dsInstance.logger = ds.logger - return dsInstance, nil + zabbixSettings, err := readZabbixSettings(dsInfo) + if err != nil { + return nil, err + } + + return &ZabbixDatasourceInstance{ + dsInfo: dsInfo, + zabbixAPI: zabbixAPI, + Settings: zabbixSettings, + queryCache: NewCache(zabbixSettings.CacheTTL, 10*time.Minute), + logger: log.New(), + }, nil } // CheckHealth checks if the plugin is running properly @@ -114,59 +108,36 @@ func (ds *ZabbixDatasource) QueryData(ctx context.Context, req *backend.QueryDat return qdr, nil } -// func (p *ZabbixPlugin) GetDatasourceById(datasourceId int64) (*ZabbixDatasourceInstance, error) { -// } +// GetDatasource Returns cached datasource or creates new one +func (ds *ZabbixDatasource) GetDatasource(pluginContext backend.PluginContext) (*ZabbixDatasourceInstance, error) { + dsSettings := pluginContext.DataSourceInstanceSettings + dsKey := fmt.Sprintf("%d-%d", pluginContext.OrgID, dsSettings.ID) + // Get hash to check if settings changed + dsInfoHash := HashDatasourceInfo(dsSettings) -// newZabbixDatasource returns an initialized ZabbixDatasource -func newZabbixDatasource(dsInfo *backend.DataSourceInstanceSettings) (*ZabbixDatasourceInstance, error) { - zabbixURLStr := dsInfo.URL - zabbixURL, err := url.Parse(zabbixURLStr) + if cachedData, ok := ds.datasourceCache.Get(dsKey); ok { + if cachedDS, ok := cachedData.(*ZabbixDatasourceInstance); ok { + cachedDSHash := HashDatasourceInfo(cachedDS.dsInfo) + if cachedDSHash == dsInfoHash { + return cachedDS, nil + } + ds.logger.Debug("Data source settings changed", "org", pluginContext.OrgID, "id", dsSettings.ID, "name", dsSettings.Name) + } + } + + ds.logger.Debug("Initializing data source", "org", pluginContext.OrgID, "id", dsSettings.ID, "name", dsSettings.Name) + dsInstance, err := NewZabbixDatasourceInstance(pluginContext.DataSourceInstanceSettings) if err != nil { + ds.logger.Error("Error initializing datasource", "error", err) return nil, err } - zabbixAPI, err := zabbixapi.New(dsInfo.URL) - if err != nil { - return nil, err - } - - zabbixSettings, err := readZabbixSettings(dsInfo) - if err != nil { - return nil, err - } - - return &ZabbixDatasourceInstance{ - zabbixAPI: zabbixAPI, - url: zabbixURL, - dsInfo: dsInfo, - Settings: zabbixSettings, - queryCache: NewCache(zabbixSettings.CacheTTL, 10*time.Minute), - httpClient: &http.Client{ - Transport: &http.Transport{ - TLSClientConfig: &tls.Config{ - Renegotiation: tls.RenegotiateFreelyAsClient, - }, - Proxy: http.ProxyFromEnvironment, - Dial: (&net.Dialer{ - Timeout: 30 * time.Second, - KeepAlive: 30 * time.Second, - }).Dial, - TLSHandshakeTimeout: 10 * time.Second, - ExpectContinueTimeout: 1 * time.Second, - MaxIdleConns: 100, - IdleConnTimeout: 90 * time.Second, - }, - Timeout: time.Duration(time.Second * 30), - }, - }, nil + ds.datasourceCache.Set(dsKey, dsInstance) + return dsInstance, nil } func readZabbixSettings(dsInstanceSettings *backend.DataSourceInstanceSettings) (*ZabbixDatasourceSettings, error) { - zabbixSettingsDTO := &ZabbixDatasourceSettingsDTO{ - TrendsFrom: "7d", - TrendsRange: "4d", - CacheTTL: "1h", - } + zabbixSettingsDTO := &ZabbixDatasourceSettingsDTO{} err := json.Unmarshal(dsInstanceSettings.JSONData, &zabbixSettingsDTO) if err != nil { @@ -207,32 +178,3 @@ func readZabbixSettings(dsInstanceSettings *backend.DataSourceInstanceSettings) return zabbixSettings, nil } - -// GetDatasource Returns cached datasource or creates new one -func (ds *ZabbixDatasource) GetDatasource(pluginContext backend.PluginContext) (*ZabbixDatasourceInstance, error) { - dsSettings := pluginContext.DataSourceInstanceSettings - dsInfoHash := HashDatasourceInfo(dsSettings) - - if cachedData, ok := ds.datasourceCache.Get(dsInfoHash); ok { - if cachedDS, ok := cachedData.(*ZabbixDatasourceInstance); ok { - return cachedDS, nil - } - } - - ds.logger.Debug(fmt.Sprintf("Datasource cache miss (Org %d Id %d '%s' %s)", pluginContext.OrgID, dsSettings.ID, dsSettings.Name, dsInfoHash)) - - dsInstance, err := ds.NewZabbixDatasource(pluginContext.DataSourceInstanceSettings) - if err != nil { - ds.logger.Error("Error initializing datasource", "error", err) - return nil, err - } - - ds.datasourceCache.Set(dsInfoHash, dsInstance) - return dsInstance, nil -} - -func BuildAPIResponse(responseData *interface{}) (*ZabbixAPIResourceResponse, error) { - return &ZabbixAPIResourceResponse{ - Result: *responseData, - }, nil -} diff --git a/pkg/models.go b/pkg/models.go index 39509aa..16471d0 100644 --- a/pkg/models.go +++ b/pkg/models.go @@ -97,102 +97,3 @@ func ReadQuery(query backend.DataQuery) (QueryModel, error) { model.TimeRange = query.TimeRange return model, nil } - -// Old models - -type connectionTestResponse struct { - ZabbixVersion string `json:"zabbixVersion"` - DbConnectorStatus *dbConnectionStatus `json:"dbConnectorStatus"` -} - -type dbConnectionStatus struct { - DsType string `json:"dsType"` - DsName string `json:"dsName"` -} - -type requestModel struct { - Target queryRequest `json:"target,omitempty"` -} - -type queryRequest struct { - Method string `json:"method,omitempty"` - Params ZabbixAPIParams `json:"params,omitempty"` -} - -type zabbixParamOutput struct { - Mode string - Fields []string -} - -func (p *zabbixParamOutput) MarshalJSON() ([]byte, error) { - if p.Mode != "" { - return json.Marshal(p.Mode) - } - - return json.Marshal(p.Fields) -} - -func (p *zabbixParamOutput) UnmarshalJSON(data []byte) error { - if p == nil { - return fmt.Errorf("zabbixParamOutput: UnmarshalJSON on nil pointer") - } - - var strArray []string - err := json.Unmarshal(data, &strArray) - if err == nil { - p.Fields = strArray - return nil - } - - var str string - err = json.Unmarshal(data, &str) - if err == nil { - p.Mode = str - return nil - } - - return fmt.Errorf("Unsupported type: %w", err) - -} - -type ZabbixAPIParamsLegacy struct { - Output *zabbixParamOutput `json:"output,omitempty"` - SortField string `json:"sortfield,omitempty"` - SortOrder string `json:"sortorder,omitempty"` - Filter map[string]interface{} `json:"filter,omitempty"` - - // Login - User string `json:"user,omitempty"` - Password string `json:"password,omitempty"` - - // Item GET - WebItems bool `json:"webitems,omitempty"` - SelectHosts interface{} `json:"selectHosts,omitempty"` - ItemIDs []string `json:"itemids,omitempty"` - GroupIDs []string `json:"groupids,omitempty"` - HostIDs []string `json:"hostids,omitempty"` - AppIDs []string `json:"applicationids,omitempty"` - - // event.get - SelectAcknowledges interface{} `json:"select_acknowledges,omitempty"` - ObjectIDs []string `json:"objectids,omitempty"` - Value interface{} `json:"value,omitempty"` - - // trigger.get - ExpandDescription bool `json:"expandDescription,omitempty"` - ExpandData bool `json:"expandData,omitempty"` - ExpandComment bool `json:"expandComment,omitempty"` - Monitored bool `json:"monitored,omitempty"` - SkipDependent bool `json:"skipDependent,omitempty"` - SelectLastEvent interface{} `json:"selectLastEvent,omitempty"` - - // Host Group GET - RealHosts bool `json:"real_hosts,omitempty"` - - // History GET - History *int `json:"history,omitempty,string"` - - // History/Trends GET - TimeFrom int64 `json:"time_from,omitempty"` - TimeTill int64 `json:"time_till,omitempty"` -} diff --git a/pkg/zabbix.go b/pkg/zabbix.go index e37fb1b..4851d84 100644 --- a/pkg/zabbix.go +++ b/pkg/zabbix.go @@ -60,6 +60,12 @@ func (ds *ZabbixDatasourceInstance) ZabbixAPIQuery(ctx context.Context, apiReq * return BuildAPIResponse(&result) } +func BuildAPIResponse(responseData *interface{}) (*ZabbixAPIResourceResponse, error) { + return &ZabbixAPIResourceResponse{ + Result: *responseData, + }, nil +} + // TestConnection checks authentication and version of the Zabbix API and returns that info func (ds *ZabbixDatasourceInstance) TestConnection(ctx context.Context) (string, error) { _, err := ds.getAllGroups(ctx) diff --git a/pkg/zabbixapi/models.go b/pkg/zabbixapi/models.go index 61f9f02..91b5680 100644 --- a/pkg/zabbixapi/models.go +++ b/pkg/zabbixapi/models.go @@ -1,8 +1,15 @@ package zabbixapi +import "encoding/json" + type ZabbixAPIRequest struct { Method string `json:"method"` Params ZabbixAPIParams `json:"params,omitempty"` } +func (r *ZabbixAPIRequest) String() string { + jsonRequest, _ := json.Marshal(r.Params) + return r.Method + string(jsonRequest) +} + type ZabbixAPIParams = map[string]interface{}