Skip to content

Commit

Permalink
Collect ClientSettingsPolicy, ObservabilityPolicy, and NginxProxy cou…
Browse files Browse the repository at this point in the history
…nt (#2179)

Collect count for ClientSettingsPolicies attached at the Gateway level, ClientSettingsPolicies attached at the Route level, ObservabilityPolicies, and NginxProxy.

Problem: I want to collect the number of ClientSettings, Observability, and NginxProxy Policies used in NGF for each context they are used in.

Solution: Collect the counts of the resources.

Testing: Manual testing and addition to unit tests.
  • Loading branch information
bjee19 authored Jul 8, 2024
1 parent 6061483 commit 8884c70
Show file tree
Hide file tree
Showing 7 changed files with 147 additions and 31 deletions.
31 changes: 31 additions & 0 deletions internal/mode/static/telemetry/collector.go
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ import (
k8sversion "k8s.io/apimachinery/pkg/util/version"
"sigs.k8s.io/controller-runtime/pkg/client"

"github.com/nginxinc/nginx-gateway-fabric/internal/framework/kinds"
"github.com/nginxinc/nginx-gateway-fabric/internal/mode/static/config"
"github.com/nginxinc/nginx-gateway-fabric/internal/mode/static/state/dataplane"
"github.com/nginxinc/nginx-gateway-fabric/internal/mode/static/state/graph"
Expand Down Expand Up @@ -71,6 +72,15 @@ type NGFResourceCounts struct {
GRPCRouteCount int64
// BackendTLSPolicyCount is the number of relevant BackendTLSPolicies.
BackendTLSPolicyCount int64
// GatewayAttachedClientSettingsPolicyCount is the number of relevant ClientSettingsPolicies
// attached at the Gateway level.
GatewayAttachedClientSettingsPolicyCount int64
// RouteAttachedClientSettingsPolicyCount is the number of relevant ClientSettingsPolicies attached at the Route level.
RouteAttachedClientSettingsPolicyCount int64
// ObservabilityPolicyCount is the number of relevant ObservabilityPolicies.
ObservabilityPolicyCount int64
// NginxProxyCount is the number of NginxProxies.
NginxProxyCount int64
}

// DataCollectorConfig holds configuration parameters for DataCollectorImpl.
Expand Down Expand Up @@ -190,6 +200,27 @@ func collectGraphResourceCount(

ngfResourceCounts.BackendTLSPolicyCount = int64(len(g.BackendTLSPolicies))

for policyKey, policy := range g.NGFPolicies {
switch policyKey.GVK.Kind {
case kinds.ClientSettingsPolicy:
if len(policy.TargetRefs) == 0 {
continue
}

if policy.TargetRefs[0].Kind == kinds.Gateway {
ngfResourceCounts.GatewayAttachedClientSettingsPolicyCount++
} else {
ngfResourceCounts.RouteAttachedClientSettingsPolicyCount++
}
case kinds.ObservabilityPolicy:
ngfResourceCounts.ObservabilityPolicyCount++
}
}

if g.NginxProxy != nil {
ngfResourceCounts.NginxProxyCount = 1
}

return ngfResourceCounts, nil
}

Expand Down
96 changes: 74 additions & 22 deletions internal/mode/static/telemetry/collector_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,11 +12,13 @@ import (
appsv1 "k8s.io/api/apps/v1"
v1 "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/runtime/schema"
"k8s.io/apimachinery/pkg/types"
"sigs.k8s.io/controller-runtime/pkg/client"
gatewayv1 "sigs.k8s.io/gateway-api/apis/v1"

"github.com/nginxinc/nginx-gateway-fabric/internal/framework/events/eventsfakes"
"github.com/nginxinc/nginx-gateway-fabric/internal/framework/kinds"
"github.com/nginxinc/nginx-gateway-fabric/internal/mode/static/config"
"github.com/nginxinc/nginx-gateway-fabric/internal/mode/static/state/dataplane"
"github.com/nginxinc/nginx-gateway-fabric/internal/mode/static/state/graph"
Expand Down Expand Up @@ -304,6 +306,25 @@ var _ = Describe("Collector", Ordered, func() {
{Namespace: "test", Name: "backendTLSPolicy-2"}: {},
{Namespace: "test", Name: "backendTLSPolicy-3"}: {},
},
NGFPolicies: map[graph.PolicyKey]*graph.Policy{
{
NsName: types.NamespacedName{Namespace: "test", Name: "ClientSettingsPolicy-1"},
GVK: schema.GroupVersionKind{Kind: kinds.ClientSettingsPolicy},
}: {TargetRefs: []graph.PolicyTargetRef{{Kind: kinds.Gateway}}},
{
NsName: types.NamespacedName{Namespace: "test", Name: "ClientSettingsPolicy-2"},
GVK: schema.GroupVersionKind{Kind: kinds.ClientSettingsPolicy},
}: {TargetRefs: []graph.PolicyTargetRef{{Kind: kinds.HTTPRoute}}},
{
NsName: types.NamespacedName{Namespace: "test", Name: "ClientSettingsPolicy-3"},
GVK: schema.GroupVersionKind{Kind: kinds.ClientSettingsPolicy},
}: {TargetRefs: []graph.PolicyTargetRef{{Kind: kinds.GRPCRoute}}},
{
NsName: types.NamespacedName{Namespace: "test", Name: "ObservabilityPolicy-1"},
GVK: schema.GroupVersionKind{Kind: kinds.ObservabilityPolicy},
}: {},
},
NginxProxy: &graph.NginxProxy{},
}

config := &dataplane.Configuration{
Expand Down Expand Up @@ -342,14 +363,18 @@ var _ = Describe("Collector", Ordered, func() {

expData.ClusterNodeCount = 3
expData.NGFResourceCounts = telemetry.NGFResourceCounts{
GatewayCount: 3,
GatewayClassCount: 3,
HTTPRouteCount: 3,
SecretCount: 3,
ServiceCount: 3,
EndpointCount: 4,
GRPCRouteCount: 2,
BackendTLSPolicyCount: 3,
GatewayCount: 3,
GatewayClassCount: 3,
HTTPRouteCount: 3,
SecretCount: 3,
ServiceCount: 3,
EndpointCount: 4,
GRPCRouteCount: 2,
BackendTLSPolicyCount: 3,
GatewayAttachedClientSettingsPolicyCount: 1,
RouteAttachedClientSettingsPolicyCount: 2,
ObservabilityPolicyCount: 1,
NginxProxyCount: 1,
}
expData.ClusterVersion = "1.29.2"
expData.ClusterPlatform = "kind"
Expand Down Expand Up @@ -495,6 +520,25 @@ var _ = Describe("Collector", Ordered, func() {
ReferencedServices: map[types.NamespacedName]struct{}{
client.ObjectKeyFromObject(svc): {},
},
NGFPolicies: map[graph.PolicyKey]*graph.Policy{
{
NsName: types.NamespacedName{Namespace: "test", Name: "ClientSettingsPolicy-1"},
GVK: schema.GroupVersionKind{Kind: kinds.ClientSettingsPolicy},
}: {TargetRefs: []graph.PolicyTargetRef{{Kind: kinds.Gateway}}},
{
NsName: types.NamespacedName{Namespace: "test", Name: "ClientSettingsPolicy-2"},
GVK: schema.GroupVersionKind{Kind: kinds.ClientSettingsPolicy},
}: {TargetRefs: []graph.PolicyTargetRef{{Kind: kinds.HTTPRoute}}},
{
NsName: types.NamespacedName{Namespace: "test", Name: "ClientSettingsPolicy-empty"},
GVK: schema.GroupVersionKind{Kind: kinds.ClientSettingsPolicy},
}: {},
{
NsName: types.NamespacedName{Namespace: "test", Name: "ObservabilityPolicy-1"},
GVK: schema.GroupVersionKind{Kind: kinds.ObservabilityPolicy},
}: {},
},
NginxProxy: &graph.NginxProxy{},
}

config1 = &dataplane.Configuration{
Expand Down Expand Up @@ -557,12 +601,16 @@ var _ = Describe("Collector", Ordered, func() {
fakeConfigurationGetter.GetLatestConfigurationReturns(config1)

expData.NGFResourceCounts = telemetry.NGFResourceCounts{
GatewayCount: 1,
GatewayClassCount: 1,
HTTPRouteCount: 1,
SecretCount: 1,
ServiceCount: 1,
EndpointCount: 1,
GatewayCount: 1,
GatewayClassCount: 1,
HTTPRouteCount: 1,
SecretCount: 1,
ServiceCount: 1,
EndpointCount: 1,
GatewayAttachedClientSettingsPolicyCount: 1,
RouteAttachedClientSettingsPolicyCount: 1,
ObservabilityPolicyCount: 1,
NginxProxyCount: 1,
}

data, err := dataCollector.Collect(ctx)
Expand All @@ -575,14 +623,18 @@ var _ = Describe("Collector", Ordered, func() {
fakeGraphGetter.GetLatestGraphReturns(&graph.Graph{})
fakeConfigurationGetter.GetLatestConfigurationReturns(invalidUpstreamsConfig)
expData.NGFResourceCounts = telemetry.NGFResourceCounts{
GatewayCount: 0,
GatewayClassCount: 0,
HTTPRouteCount: 0,
SecretCount: 0,
ServiceCount: 0,
EndpointCount: 0,
GRPCRouteCount: 0,
BackendTLSPolicyCount: 0,
GatewayCount: 0,
GatewayClassCount: 0,
HTTPRouteCount: 0,
SecretCount: 0,
ServiceCount: 0,
EndpointCount: 0,
GRPCRouteCount: 0,
BackendTLSPolicyCount: 0,
GatewayAttachedClientSettingsPolicyCount: 0,
RouteAttachedClientSettingsPolicyCount: 0,
ObservabilityPolicyCount: 0,
NginxProxyCount: 0,
}

data, err := dataCollector.Collect(ctx)
Expand Down
13 changes: 13 additions & 0 deletions internal/mode/static/telemetry/data.avdl
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,19 @@ Each value is either 'true' or 'false' for boolean flags and 'default' or 'user-
/** BackendTLSPolicyCount is the number of relevant BackendTLSPolicies. */
long? BackendTLSPolicyCount = null;

/** GatewayAttachedClientSettingsPolicyCount is the number of relevant ClientSettingsPolicies
attached at the Gateway level. */
long? GatewayAttachedClientSettingsPolicyCount = null;

/** RouteAttachedClientSettingsPolicyCount is the number of relevant ClientSettingsPolicies attached at the Route level. */
long? RouteAttachedClientSettingsPolicyCount = null;

/** ObservabilityPolicyCount is the number of relevant ObservabilityPolicies. */
long? ObservabilityPolicyCount = null;

/** NginxProxyCount is the number of NginxProxies. */
long? NginxProxyCount = null;

/** NGFReplicaCount is the number of replicas of the NGF Pod. */
long? NGFReplicaCount = null;

Expand Down
28 changes: 20 additions & 8 deletions internal/mode/static/telemetry/data_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,14 +24,18 @@ func TestDataAttributes(t *testing.T) {
FlagNames: []string{"test-flag"},
FlagValues: []string{"test-value"},
NGFResourceCounts: NGFResourceCounts{
GatewayCount: 1,
GatewayClassCount: 2,
HTTPRouteCount: 3,
SecretCount: 4,
ServiceCount: 5,
EndpointCount: 6,
GRPCRouteCount: 7,
BackendTLSPolicyCount: 8,
GatewayCount: 1,
GatewayClassCount: 2,
HTTPRouteCount: 3,
SecretCount: 4,
ServiceCount: 5,
EndpointCount: 6,
GRPCRouteCount: 7,
BackendTLSPolicyCount: 8,
GatewayAttachedClientSettingsPolicyCount: 9,
RouteAttachedClientSettingsPolicyCount: 10,
ObservabilityPolicyCount: 11,
NginxProxyCount: 12,
},
NGFReplicaCount: 3,
}
Expand All @@ -57,6 +61,10 @@ func TestDataAttributes(t *testing.T) {
attribute.Int64("EndpointCount", 6),
attribute.Int64("GRPCRouteCount", 7),
attribute.Int64("BackendTLSPolicyCount", 8),
attribute.Int64("GatewayAttachedClientSettingsPolicyCount", 9),
attribute.Int64("RouteAttachedClientSettingsPolicyCount", 10),
attribute.Int64("ObservabilityPolicyCount", 11),
attribute.Int64("NginxProxyCount", 12),
attribute.Int64("NGFReplicaCount", 3),
}

Expand Down Expand Up @@ -90,6 +98,10 @@ func TestDataAttributesWithEmptyData(t *testing.T) {
attribute.Int64("EndpointCount", 0),
attribute.Int64("GRPCRouteCount", 0),
attribute.Int64("BackendTLSPolicyCount", 0),
attribute.Int64("GatewayAttachedClientSettingsPolicyCount", 0),
attribute.Int64("RouteAttachedClientSettingsPolicyCount", 0),
attribute.Int64("ObservabilityPolicyCount", 0),
attribute.Int64("NginxProxyCount", 0),
attribute.Int64("NGFReplicaCount", 0),
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,10 @@ func (d *NGFResourceCounts) Attributes() []attribute.KeyValue {
attrs = append(attrs, attribute.Int64("EndpointCount", d.EndpointCount))
attrs = append(attrs, attribute.Int64("GRPCRouteCount", d.GRPCRouteCount))
attrs = append(attrs, attribute.Int64("BackendTLSPolicyCount", d.BackendTLSPolicyCount))
attrs = append(attrs, attribute.Int64("GatewayAttachedClientSettingsPolicyCount", d.GatewayAttachedClientSettingsPolicyCount))
attrs = append(attrs, attribute.Int64("RouteAttachedClientSettingsPolicyCount", d.RouteAttachedClientSettingsPolicyCount))
attrs = append(attrs, attribute.Int64("ObservabilityPolicyCount", d.ObservabilityPolicyCount))
attrs = append(attrs, attribute.Int64("NginxProxyCount", d.NginxProxyCount))


return attrs
Expand Down
2 changes: 1 addition & 1 deletion site/content/overview/product-telemetry.md
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ Telemetry data is collected once every 24 hours and sent to a service managed by
- **Deployment Replica Count:** the count of NGINX Gateway Fabric Pods.
- **Image Build Source:** whether the image was built by GitHub or locally (values are `gha`, `local`, or `unknown`). The source repository of the images is **not** collected.
- **Deployment Flags:** a list of NGINX Gateway Fabric Deployment flags that are specified by a user. The actual values of non-boolean flags are **not** collected; we only record that they are either `true` or `false` for boolean flags and `default` or `user-defined` for the rest.
- **Count of Resources:** the total count of resources related to NGINX Gateway Fabric. This includes `GatewayClasses`, `Gateways`, `HTTPRoutes`,`GRPCRoutes`, `Secrets`, `Services`, `BackendTLSPolicies`, and `Endpoints`. The data within these resources is **not** collected.
- **Count of Resources:** the total count of resources related to NGINX Gateway Fabric. This includes `GatewayClasses`, `Gateways`, `HTTPRoutes`,`GRPCRoutes`, `Secrets`, `Services`, `BackendTLSPolicies`, `ClientSettingsPolicies`, `NginxProxies`, `ObservabilityPolicies`, and `Endpoints`. The data within these resources is **not** collected.

This data is used to identify the following information:

Expand Down
4 changes: 4 additions & 0 deletions tests/suite/telemetry_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -80,6 +80,10 @@ var _ = Describe("Telemetry test with OTel collector", Label("telemetry"), func(
"EndpointCount: Int(0)",
"GRPCRouteCount: Int(0)",
"BackendTLSPolicyCount: Int(0)",
"GatewayAttachedClientSettingsPolicyCount: Int(0)",
"RouteAttachedClientSettingsPolicyCount: Int(0)",
"ObservabilityPolicyCount: Int(0)",
"NginxProxyCount: Int(0)",
"NGFReplicaCount: Int(1)",
},
)
Expand Down

0 comments on commit 8884c70

Please sign in to comment.