From 85fa234102fdf670d915b3374e5208995c369309 Mon Sep 17 00:00:00 2001 From: Nathan Verzemnieks Date: Fri, 15 Nov 2024 11:02:58 +0100 Subject: [PATCH] One more rework, logic back here but cached --- backend/config.go | 29 +++++++++++++++----- backend/datasource/instance_provider.go | 3 +- backend/datasource/instance_provider_test.go | 23 +++++++++++++--- 3 files changed, 42 insertions(+), 13 deletions(-) diff --git a/backend/config.go b/backend/config.go index 1cd2df01a..02790e881 100644 --- a/backend/config.go +++ b/backend/config.go @@ -4,6 +4,7 @@ import ( "context" "errors" "fmt" + "hash/fnv" "os" "strconv" "strings" @@ -48,13 +49,6 @@ func WithGrafanaConfig(ctx context.Context, cfg *GrafanaCfg) context.Context { return ctx } -// ProxyHashFromContext returns the hash of the client cert contents, set on -// the incoming GrafanaCfg, for use in datasource instance caching -func ProxyHashFromContext(ctx context.Context) string { - cfg := GrafanaConfigFromContext(ctx) - return cfg.Get(proxy.PluginSecureSocksProxyClientCertContentsHash) -} - type GrafanaCfg struct { config map[string]string } @@ -103,6 +97,27 @@ func (c *GrafanaCfg) Equal(c2 *GrafanaCfg) bool { return true } +// ProxyHash returns a hash of the configured proxy client cert contents +// for use in datasource instance caching. It stores the hash so it only +// needs to be calculated once per datasource instance. +func (c *GrafanaCfg) ProxyHash() string { + if c == nil { + return "" + } + contents := c.config[proxy.PluginSecureSocksProxyClientCertContents] + if contents == "" { + return "" + } + hash := c.config[proxy.PluginSecureSocksProxyClientCertContentsHash] + if hash == "" { + h := fnv.New32a() + _, _ = h.Write([]byte(contents)) + hash = fmt.Sprintf("%08x", h.Sum32()) + c.config[proxy.PluginSecureSocksProxyClientCertContentsHash] = hash + } + return hash +} + type FeatureToggles struct { // enabled is a set-like map of feature flags that are enabled. enabled map[string]struct{} diff --git a/backend/datasource/instance_provider.go b/backend/datasource/instance_provider.go index 7012c7e09..443a9c4d8 100644 --- a/backend/datasource/instance_provider.go +++ b/backend/datasource/instance_provider.go @@ -4,7 +4,6 @@ import ( "context" "errors" "fmt" - "github.com/prometheus/client_golang/prometheus" "github.com/prometheus/client_golang/prometheus/promauto" @@ -60,7 +59,7 @@ func (ip *instanceProvider) GetKey(ctx context.Context, pluginContext backend.Pl } dsID := pluginContext.DataSourceInstanceSettings.ID - proxyHash := backend.ProxyHashFromContext(ctx) + proxyHash := pluginContext.GrafanaConfig.ProxyHash() tenantID := tenant.IDFromContext(ctx) return fmt.Sprintf("%d#%s#%s", dsID, tenantID, proxyHash), nil diff --git a/backend/datasource/instance_provider_test.go b/backend/datasource/instance_provider_test.go index 6cc7d4ac4..1b089f119 100644 --- a/backend/datasource/instance_provider_test.go +++ b/backend/datasource/instance_provider_test.go @@ -36,17 +36,32 @@ func TestInstanceProvider(t *testing.T) { t.Run("When PDC is configured, datasource cache key should include its hash", func(t *testing.T) { cfg := backend.NewGrafanaCfg(map[string]string{ - proxy.PluginSecureSocksProxyClientCertContentsHash: "01234568", + proxy.PluginSecureSocksProxyClientCertContents: "whee", }) - ctx := backend.WithGrafanaConfig(context.Background(), cfg) - key, err := ip.GetKey(ctx, backend.PluginContext{ + key, err := ip.GetKey(context.Background(), backend.PluginContext{ DataSourceInstanceSettings: &backend.DataSourceInstanceSettings{ ID: 5, JSONData: []byte(`{"enableSecureSocksProxy": true}`), }, + GrafanaConfig: cfg, + }) + require.NoError(t, err) + require.Equal(t, "5##84778cf8", key) + }) + + t.Run("When PDC is configured, different cert contents give different hashes", func(t *testing.T) { + cfg := backend.NewGrafanaCfg(map[string]string{ + proxy.PluginSecureSocksProxyClientCertContents: "oh no", + }) + key, err := ip.GetKey(context.Background(), backend.PluginContext{ + DataSourceInstanceSettings: &backend.DataSourceInstanceSettings{ + ID: 6, + JSONData: []byte(`{"enableSecureSocksProxy": true}`), + }, + GrafanaConfig: cfg, }) require.NoError(t, err) - require.Equal(t, "5##01234568", key) + require.Equal(t, "6##352d64b5", key) }) t.Run("When both the configuration and updated field of current data source instance settings are equal to the cache, should return false", func(t *testing.T) {