From 7e22ce570155d2eac6c08081631757fd1a4c19fb Mon Sep 17 00:00:00 2001 From: Kevin Williams Date: Mon, 8 Jun 2026 16:19:57 -0700 Subject: [PATCH 1/2] feat: add DNS ServiceConfiguration for metering Declare DNS metering as a services.miloapis.com/ServiceConfiguration (Phase 2 of the catalog registration). Meters three signals: - zone/queries (Delta, {query}) -- authoritative query volume, the primary consumption signal, dimensioned by rcode/record_type/location - zone/hosted (Gauge, {zone}) -- active hosted-zone footprint - recordset/active (Gauge, {recordset}) -- managed record-set inventory Monitored resource types DNSZone and DNSRecordSet, billing routing wired to both. The services-operator fans this out into MeterDefinition and MonitoredResourceType billing CRDs. Ships Published in the same components/service-catalog bundle, so infra's existing Flux Kustomization picks it up automatically. Emitting zone/queries events from the PowerDNS data plane remains as follow-up usage-pipeline work. --- config/components/service-catalog/README.md | 11 +-- .../service-catalog/kustomization.yaml | 7 +- ...ces_v1alpha1_serviceconfiguration_dns.yaml | 77 +++++++++++++++++++ 3 files changed, 86 insertions(+), 9 deletions(-) create mode 100644 config/components/service-catalog/services_v1alpha1_serviceconfiguration_dns.yaml diff --git a/config/components/service-catalog/README.md b/config/components/service-catalog/README.md index 85b8b5e..e212024 100644 --- a/config/components/service-catalog/README.md +++ b/config/components/service-catalog/README.md @@ -15,7 +15,7 @@ API-surface repo. | Kind | Name | What it declares | | ---------------------- | ----------------------------- | --------------------------------------------------------------------------- | | `Service` | `dns-networking-miloapis-com` | `serviceName`, display metadata, producer owner. | -| `ServiceConfiguration` | `dns-networking-miloapis-com` | DNS MonitoredResourceTypes, metrics, and billing routing. _(Phase 2 — TBD)_ | +| `ServiceConfiguration` | `dns-networking-miloapis-com` | DNS MonitoredResourceTypes, metrics, and billing routing. | Ships in `phase: Published`. @@ -40,10 +40,11 @@ objects stamped `app.kubernetes.io/managed-by: services-operator`. Producers must not author those downstream CRDs directly — edit the `ServiceConfiguration` and let the fan-out catch up. -The DNS `ServiceConfiguration` is tracked as Phase 2 of the catalog -registration (metering): query volume, hosted zones, and record-set -inventory. See the -[catalog registration issue](https://github.com/datum-cloud/dns-operator/issues/44). +The DNS `ServiceConfiguration` meters three signals: authoritative +query volume (`zone/queries`), hosted-zone footprint (`zone/hosted`), +and record-set inventory (`recordset/active`). Declaring `zone/queries` +is the metering contract; emitting those query events from the PowerDNS +data plane is the remaining usage-pipeline work. ## Immutability after `Published` diff --git a/config/components/service-catalog/kustomization.yaml b/config/components/service-catalog/kustomization.yaml index 34ceb72..7249343 100644 --- a/config/components/service-catalog/kustomization.yaml +++ b/config/components/service-catalog/kustomization.yaml @@ -10,10 +10,9 @@ kind: Kustomization # # 1. The `Service` itself (`dns-networking-miloapis-com`), which carries # identity (`serviceName`), display metadata, and producer owner. -# (Phase 1 — service registration.) # 2. A single `ServiceConfiguration` (same name, different Kind) that -# will declare the DNS MonitoredResourceTypes, metrics, and billing -# routing. (Phase 2 — metering; not yet authored.) +# declares the DNS MonitoredResourceTypes, metrics, and billing +# routing. # # Per billing's `emitting-usage.md`, the `ServiceConfiguration` is the # *only* document a producer authors for billing: the services-operator @@ -27,4 +26,4 @@ kind: Kustomization # repo, the same way other services publish their catalog entries. resources: - services_v1alpha1_service_dns.yaml - # - services_v1alpha1_serviceconfiguration_dns.yaml # added in Phase 2 + - services_v1alpha1_serviceconfiguration_dns.yaml diff --git a/config/components/service-catalog/services_v1alpha1_serviceconfiguration_dns.yaml b/config/components/service-catalog/services_v1alpha1_serviceconfiguration_dns.yaml new file mode 100644 index 0000000..562c9ec --- /dev/null +++ b/config/components/service-catalog/services_v1alpha1_serviceconfiguration_dns.yaml @@ -0,0 +1,77 @@ +# SPDX-License-Identifier: AGPL-3.0-only + +# DNS metering. The services-operator fans this out into billing +# MeterDefinition/MonitoredResourceType objects; don't author those directly. +apiVersion: services.miloapis.com/v1alpha1 +kind: ServiceConfiguration +metadata: + labels: + app.kubernetes.io/name: dns-operator + app.kubernetes.io/managed-by: kustomize + name: dns-networking-miloapis-com +spec: + serviceRef: + name: dns-networking-miloapis-com + phase: Published + version: v1 + monitoredResourceTypes: + - type: dns.networking.miloapis.com/DNSZone + displayName: DNS Zone + description: | + An authoritative DNS zone, billed on per-zone footprint (zone/hosted) + and authoritative query volume (zone/queries). + gvk: + group: dns.networking.miloapis.com + kind: DNSZone + labels: + - name: location + description: Datum point-of-presence / region serving the zone or query. + - name: rcode + description: DNS response code for answered queries (NOERROR, NXDOMAIN, SERVFAIL). + - name: record_type + description: Queried record type (A, AAAA, CNAME, TXT, MX, ...). + - type: dns.networking.miloapis.com/DNSRecordSet + displayName: DNS Record Set + description: A set of records of one type under a zone, billed as managed inventory. + gvk: + group: dns.networking.miloapis.com + kind: DNSRecordSet + labels: + - name: location + description: Datum point-of-presence / region hosting the record set. + - name: record_type + description: Record type of the set (A, AAAA, CNAME, TXT, MX, ...). + metrics: + - name: dns.networking.miloapis.com/zone/queries + displayName: DNS Queries + description: Authoritative queries answered for a zone (primary consumption signal). + kind: Delta + unit: "{query}" + dimensions: + - rcode + - record_type + - location + - name: dns.networking.miloapis.com/zone/hosted + displayName: Hosted DNS Zones + description: Active hosted-zone footprint (gauge, 1 per active DNSZone). + kind: Gauge + unit: "{zone}" + dimensions: + - location + - name: dns.networking.miloapis.com/recordset/active + displayName: Active DNS Record Sets + description: Record sets under management (gauge, 1 per active DNSRecordSet). + kind: Gauge + unit: "{recordset}" + dimensions: + - record_type + - location + billing: + consumerDestinations: + - monitoredResourceType: dns.networking.miloapis.com/DNSZone + metrics: + - dns.networking.miloapis.com/zone/queries + - dns.networking.miloapis.com/zone/hosted + - monitoredResourceType: dns.networking.miloapis.com/DNSRecordSet + metrics: + - dns.networking.miloapis.com/recordset/active From 051ff61d66d7b05cdb1fc381cbd66c3bf7bbca10 Mon Sep 17 00:00:00 2001 From: Kevin Williams Date: Mon, 15 Jun 2026 16:45:48 -0700 Subject: [PATCH 2/2] fix: address review feedback on DNS ServiceConfiguration metering MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - Rename zone/hosted → zones (simpler name) - Replace recordset/active with records/active, attributed to DNSZone - Drop DNSRecordSet monitored resource type; all metrics now route through DNSZone, sourcing record count from Status.RecordCount which the zone controller already maintains --- ...ces_v1alpha1_serviceconfiguration_dns.yaml | 32 ++++++------------- 1 file changed, 10 insertions(+), 22 deletions(-) diff --git a/config/components/service-catalog/services_v1alpha1_serviceconfiguration_dns.yaml b/config/components/service-catalog/services_v1alpha1_serviceconfiguration_dns.yaml index 562c9ec..e22b3ed 100644 --- a/config/components/service-catalog/services_v1alpha1_serviceconfiguration_dns.yaml +++ b/config/components/service-catalog/services_v1alpha1_serviceconfiguration_dns.yaml @@ -18,8 +18,9 @@ spec: - type: dns.networking.miloapis.com/DNSZone displayName: DNS Zone description: | - An authoritative DNS zone, billed on per-zone footprint (zone/hosted) - and authoritative query volume (zone/queries). + An authoritative DNS zone, billed on per-zone footprint (zones), + authoritative query volume (zone/queries), and total record inventory + (records/active via Status.RecordCount). gvk: group: dns.networking.miloapis.com kind: DNSZone @@ -30,17 +31,6 @@ spec: description: DNS response code for answered queries (NOERROR, NXDOMAIN, SERVFAIL). - name: record_type description: Queried record type (A, AAAA, CNAME, TXT, MX, ...). - - type: dns.networking.miloapis.com/DNSRecordSet - displayName: DNS Record Set - description: A set of records of one type under a zone, billed as managed inventory. - gvk: - group: dns.networking.miloapis.com - kind: DNSRecordSet - labels: - - name: location - description: Datum point-of-presence / region hosting the record set. - - name: record_type - description: Record type of the set (A, AAAA, CNAME, TXT, MX, ...). metrics: - name: dns.networking.miloapis.com/zone/queries displayName: DNS Queries @@ -51,18 +41,18 @@ spec: - rcode - record_type - location - - name: dns.networking.miloapis.com/zone/hosted + - name: dns.networking.miloapis.com/zones displayName: Hosted DNS Zones description: Active hosted-zone footprint (gauge, 1 per active DNSZone). kind: Gauge unit: "{zone}" dimensions: - location - - name: dns.networking.miloapis.com/recordset/active - displayName: Active DNS Record Sets - description: Record sets under management (gauge, 1 per active DNSRecordSet). + - name: dns.networking.miloapis.com/records/active + displayName: Active DNS Records + description: Individual DNS records under management (gauge, counted across all record sets). kind: Gauge - unit: "{recordset}" + unit: "{record}" dimensions: - record_type - location @@ -71,7 +61,5 @@ spec: - monitoredResourceType: dns.networking.miloapis.com/DNSZone metrics: - dns.networking.miloapis.com/zone/queries - - dns.networking.miloapis.com/zone/hosted - - monitoredResourceType: dns.networking.miloapis.com/DNSRecordSet - metrics: - - dns.networking.miloapis.com/recordset/active + - dns.networking.miloapis.com/zones + - dns.networking.miloapis.com/records/active