Repository navigation
Conversation
etomm
force-pushed
the
fix/ingress-path-specificity-order
branch
from
November 5, 2026 07:58
ee5b716 to
c459435
Compare
etomm
force-pushed
the
fix/ingress-path-specificity-order
branch
from
November 5, 2026 08:04
c459435 to
4eae320
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Description
Cloudflare evaluates tunnel ingress rules in order, first match wins.
The ingress aggregation currently sorts rules lexicographically by path:
Since
""(the hostname-only catch-all) sorts before any non-empty path,a catch-all such as:
is emitted before specific paths like:
Cloudflare matches the catch-all first, so the specific path rules are never
reached. The same issue exists in
TunnelConfig.AggregateRules(), which onlysorts by source priority and hostname and does not consider path specificity.
This change orders rules by path specificity before deterministic tie-breakers:
Applied to:
internal/controller/ingress/converters.go—buildIngressRulesinternal/controller/tunnelconfig/types.go—AggregateRulesBoth use
sort.SliceStableso equal keys preserve deterministic order.Container image namespace
The release workflow and Makefile previously hardcoded
ghcr.io/stringke/cloudflare-operator, which makes it awkward for forks tobuild and push their own images without editing files.
This change makes the image path configurable via
IMAGE_NAME:.github/workflows/release.ymlMakefileIMAGE_NAMEcan be set as a repository/org/environment variable(
Settings → Secrets and variables → Actions → Variables), e.g.IMAGE_NAME=myuser/cloudflare-operator. When it is not set, the upstreamstringke/cloudflare-operatorimage name is used.Type of Change
Related Issues
None.
Checklist
make test) (relevant package tests pass; fullmake testnot run locally)make lint) (not run locally)make manifests generate) (no API/CRD changes)Testing
Added
TestAggregateRulesOrdersByPathSpecificitycovering:/api/v2before/apiCommands run:
All passed. Also validated
.github/workflows/release.ymlparses as YAML.The Docker push path was not run locally; it still requires a valid GHCR login
for the target namespace.
Additional Notes
No API or CRD changes for the ingress ordering fix. The behavior for disjoint
paths is unchanged; the fix only affects ordering where a hostname catch-all
would otherwise shadow more specific path rules.
The
IMAGE_NAMEchange is configuration-only. Forks should set the repositoryvariable to a lowercase GHCR path, e.g.
myuser/cloudflare-operator.Alternative
Another option would be to simply invert the comparison:
This would invert the sort, putting path prefixes before their descendants.
It works for the common prefix-extension case and moves the empty catch-all
last, but it does not guarantee longest-path-first ordering for unrelated
paths. The explicit specificity sort is used instead because it is deterministic
and easier to reason about.