Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: Add dedicated Alertmanager datasource #14

Merged
merged 1 commit into from
Mar 25, 2024
Merged
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
102 changes: 64 additions & 38 deletions pkg/reconcileOrg.go
Original file line number Diff line number Diff line change
Expand Up @@ -39,12 +39,12 @@ func reconcileOrgBasic(grafanaOrgLookup map[string]grafana.Org, grafanaClient *G
}

func reconcileOrgSettings(config Config, org *grafana.Org, orgName string, grafanaClient *GrafanaClient, dashboards []Dashboard) error {
dataSource, err := reconcileOrgDataSource(config, org, orgName, grafanaClient)
err := reconcileOrgDataSources(config, org, orgName, grafanaClient)
if err != nil {
return err
}
for _, dashboard := range dashboards {
err = reconcileOrgDashboard(org, dataSource, grafanaClient, dashboard)
err = reconcileOrgDashboard(org, grafanaClient, dashboard)
if err != nil {
return err
}
Expand All @@ -53,7 +53,7 @@ func reconcileOrgSettings(config Config, org *grafana.Org, orgName string, grafa
return nil
}

func reconcileOrgDataSource(config Config, org *grafana.Org, orgName string, grafanaClient *GrafanaClient) (*grafana.DataSource, error) {
func reconcileOrgDataSources(config Config, org *grafana.Org, orgName string, grafanaClient *GrafanaClient) error {
secureJSONData := map[string]interface{}{
"httpHeaderValue1": orgName,
}
Expand All @@ -62,10 +62,10 @@ func reconcileOrgDataSource(config Config, org *grafana.Org, orgName string, gra
secureJSONData["basicAuthPassword"] = config.GrafanaDatasourcePassword
}

// If you add/remove fields here you must also adjust the 'if' statement further down
desiredDataSource := &grafana.DataSource{
// If you add/remove fields here you must also adjust the 'if' statement in reconcileOrgDataSource()
prometheusSource := &grafana.DataSource{
Name: "Mimir",
URL: config.GrafanaDatasourceUrl,
URL: config.GrafanaDatasourceUrl + "/prometheus",
BasicAuth: basicAuth,
BasicAuthUser: config.GrafanaDatasourceUsername,
OrgID: org.ID, // doesn't actually do anything, we just keep it here in case it becomes relevant with some never version of the client library. The actual orgId is taken from the 'X-Grafana-Org-Id' HTTP header which is set up via grafanaConfig.OrgID
Expand All @@ -80,57 +80,83 @@ func reconcileOrgDataSource(config Config, org *grafana.Org, orgName string, gra
Access: "proxy",
}

var configuredDataSource *grafana.DataSource
configuredDataSource = nil
alertmanagerSource := &grafana.DataSource{
Name: "Mimir Alertmanager",
URL: config.GrafanaDatasourceUrl,
BasicAuth: basicAuth,
BasicAuthUser: config.GrafanaDatasourceUsername,
OrgID: org.ID, // doesn't actually do anything, we just keep it here in case it becomes relevant with some never version of the client library. The actual orgId is taken from the 'X-Grafana-Org-Id' HTTP header which is set up via grafanaConfig.OrgID
Type: "alertmanager",
IsDefault: false,
JSONData: map[string]interface{}{
"httpHeaderName1": "X-Scope-OrgID",
"httpMethod": "POST",
},
SecureJSONData: secureJSONData,
Access: "proxy",
}

dataSources, err := grafanaClient.DataSources(org)
if err != nil {
return nil, err
return err
}
if len(dataSources) > 0 {
for _, dataSource := range dataSources {
if dataSource.Name == desiredDataSource.Name {
if dataSource.URL != desiredDataSource.URL ||
dataSource.BasicAuth != desiredDataSource.BasicAuth ||
dataSource.Type != desiredDataSource.Type ||
dataSource.IsDefault != desiredDataSource.IsDefault ||
!reflect.DeepEqual(dataSource.JSONData, desiredDataSource.JSONData) ||
dataSource.Access != desiredDataSource.Access {
// note that we can't detect changed basic auth credentials (BasicAuthUser, secureJSONData) because the API does not give us the current settings
klog.Infof("Organization %d has misconfigured data source, fixing", org.ID)
desiredDataSource.ID = dataSource.ID
desiredDataSource.UID = dataSource.UID
err := grafanaClient.UpdateDataSource(org, desiredDataSource)
if err != nil {
return nil, err
}
configuredDataSource = desiredDataSource
} else {
configuredDataSource = dataSource
}
} else {
klog.Infof("Organization %d has invalid data source %d %s, removing", org.ID, dataSource.ID, dataSource.Name)
err = grafanaClient.DeleteDataSource(org, dataSource.ID)

reconcileOrgDataSource(org, dataSources, prometheusSource, grafanaClient)
reconcileOrgDataSource(org, dataSources, alertmanagerSource, grafanaClient)

for _, dataSource := range dataSources {
if dataSource.Name != prometheusSource.Name && dataSource.Name != alertmanagerSource.Name {
klog.Infof("Organization %d has invalid data source %d %s, removing", org.ID, dataSource.ID, dataSource.Name)
err = grafanaClient.DeleteDataSource(org, dataSource.ID)
if err != nil {
return err
}
}
}

return nil
}

func reconcileOrgDataSource(org *grafana.Org, dataSources []*grafana.DataSource, desiredDataSource *grafana.DataSource, grafanaClient *GrafanaClient) error {
var configuredDataSource *grafana.DataSource
configuredDataSource = nil
for _, dataSource := range dataSources {
if dataSource.Name == desiredDataSource.Name {
if dataSource.URL != desiredDataSource.URL ||
dataSource.BasicAuth != desiredDataSource.BasicAuth ||
dataSource.Type != desiredDataSource.Type ||
dataSource.IsDefault != desiredDataSource.IsDefault ||
!reflect.DeepEqual(dataSource.JSONData, desiredDataSource.JSONData) ||
dataSource.Access != desiredDataSource.Access {
// note that we can't detect changed basic auth credentials (BasicAuthUser, secureJSONData) because the API does not give us the current settings
klog.Infof("Organization %d has misconfigured data source, fixing", org.ID)
desiredDataSource.ID = dataSource.ID
desiredDataSource.UID = dataSource.UID
err := grafanaClient.UpdateDataSource(org, desiredDataSource)
if err != nil {
return nil, err
return err
}
configuredDataSource = desiredDataSource
} else {
configuredDataSource = dataSource
}
}
}
if configuredDataSource == nil {
klog.Infof("Organization %d missing data source, creating", org.ID)
dataSourceId, err := grafanaClient.NewDataSource(org, desiredDataSource)
if err != nil {
return nil, err
return err
}
configuredDataSource, err = grafanaClient.DataSource(org, dataSourceId)
if err != nil {
return nil, err
return err
}
}
return configuredDataSource, nil
return nil
}

func reconcileOrgDashboard(org *grafana.Org, dataSource *grafana.DataSource, grafanaClient *GrafanaClient, dashboard Dashboard) error {
func reconcileOrgDashboard(org *grafana.Org, grafanaClient *GrafanaClient, dashboard Dashboard) error {
folder, err := reconcileOrgDashboardFolder(org, grafanaClient, dashboard.Folder)
if err != nil {
return err
Expand Down
Loading