Skip to content

feat: Limit public IPv4 claims per project - #158

Draft
scotwells wants to merge 3 commits into
fix/128-default-claim-classfrom
feat/ipv4-claims-quota
Draft

scotwells wants to merge 3 commits into
fix/128-default-claim-classfrom
feat/ipv4-claims-quota

Conversation

@scotwells

@scotwells scotwells commented Oct 28, 2026 •

Copy link
Copy Markdown
Contributor

Summary

Public IPv4 addresses are scarce, but a project's only IP limit counts every claim alike, so nothing caps how many public IPv4 addresses one project takes.

Address classes can now be marked public or private, and each claim takes its class, family and marking before quota runs, so a claim that contradicts its class is refused before it is charged.

A new per-project limit, default 2, counts only claims that are IPv4 and come from a public class.

This stacks on #129, needs milo-os/milo#940 and milo-os/service-catalog#205 deployed first, and charges nothing until the platform's public IPv4 class is marked public, which an unmarked class allows once.

Test plan

  • A claim from a public IPv4 class counts toward the new limit, and private or IPv6 claims do not
  • A claim that contradicts its class's family or marking is refused before quota runs
  • An unmarked class can be marked once, and a marked class cannot change
  • Build, lint, database-backed tests and generated code checks pass

Related to #129

scotwells and others added 3 commits October 28, 2026 17:11
Quota admission ran before the class was resolved, so a claim that named
only a class reached it with no ipFamily and any family-conditioned charge
missed it. The class is now resolved first, its name and family are written
onto the claim, and admission sees the filled object.

Key changes:
- resolve the class, refuse a family mismatch, and default className and
  ipFamily before createValidation runs
- release the class-lookup transaction immediately instead of holding it
- check namespace liveness and stamp ownerRef after admission, as before

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
A class can now say whether it hands out publicly routable or private
addresses, and every claim carries that marker from its class. Quota and
other admission checks can then tell a public address from a private one
without looking up the class themselves.

Key changes:
- add optional addressScope (Public | Private) to IPClassSpec and IPClaimSpec
- copy the class's addressScope onto the claim before admission and refuse
  a claim whose addressScope contradicts its class with AddressScopeMismatch
- let a class's addressScope be set once from unset, then hold it immutable
- keep a claim's addressScope immutable and forbid it on class references
- validate the enum in the registry strategies and regenerate OpenAPI

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Projects can now be limited in how many public IPv4 claims they hold,
separately from the overall claim limit. The charge rides on the existing
IPClaim rule and applies only to claims that are IPv4 and whose class marks
them public.

Key changes:
- add the ipam.miloapis.com/public-ipv4claims metric and the
  public-ipv4claims-per-project limit (default 2, max 256)
- charge it from the IPClaim rule via a metricCostConditions CEL guard on
  ipFamily and addressScope

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@scotwells
scotwells force-pushed the feat/ipv4-claims-quota branch from a852cc1 to 167dbaf Compare October 28, 2026 22:14
@scotwells
scotwells changed the base branch from main to fix/128-default-claim-class October 28, 2026 22:14
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant