feat: add Body scope to ApisixRoute match expressions for request body matching#2762
Merged
Conversation
…y matching Add ScopeBody to ApisixRouteHTTPMatchExprSubject.Scope, which maps to APISIX's post_arg.<name> variable. This supports request body matching for application/json, application/x-www-form-urlencoded, and multipart/form-data content types, and allows dot-notation JSON path expressions such as 'model.version' and 'messages[*].role'. Changes: - Add ScopeBody constant to shared_types.go - Add case ScopeBody in ToVars() mapping to post_arg.<name> - Add +kubebuilder:validation:Enum=...;Body to Scope field - Add +kubebuilder:validation:XValidation CEL rule: name is required when scope is not Path (uses size(self.name) > 0 for YAML safety) - Make Name field optional (omitempty) so Path scope works without name - Regenerate CRD YAML and API reference docs - Add unit tests for Body scope (simple field, nested JSON path, empty name error) - Add CEL expression tests (logic and CRD presence) - Add e2e tests: urlencoded form field matching, JSON nested path matching Closes apache#399
…dation Replace the custom cel-go based tests with the same pattern used in apisixconsumer_validation_test.go: load the generated CRD YAML, build a real Kubernetes structural schema validator, and validate ApisixRoute objects through it. This exercises both the OpenAPI enum constraints and the CEL XValidation rule without introducing additional dependencies.
Move common CRD validation infrastructure (structural schema loading and CEL validation) into crd_schema_validator_test.go so both apisixconsumer_validation_test.go and apisixroute_types_test.go share the same helper, eliminating the duplicate code flagged by golangci-lint.
nic-6443
approved these changes
May 12, 2026
shreemaan-abhishek
approved these changes
May 13, 2026
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.
Summary
Add
Bodyas a new scope value forApisixRouteHTTPMatchExprSubject, enabling request body matching inApisixRouteHTTP match expressions.How it works
When
scope: Bodyis used, the subject maps to APISIX'spost_arg.<name>variable. This variable supports:application/jsonapplication/x-www-form-urlencodedmultipart/form-dataDot-notation JSON path expressions are also supported (e.g.,
model.version,messages[*].role).Example:
Changes
api/v2/shared_types.go: addScopeBody = "Body"constantapi/v2/apisixroute_types.go:case ScopeBodyinToVars()mapping topost_arg.<name>Bodyto+kubebuilder:validation:EnumonScopefield+kubebuilder:validation:XValidationCEL rule:nameis required whenscopeis notPathNamefield optional (omitempty) soPathscope works without providing a nameapi/v2/apisixroute_types_test.go: unit tests for Body scope and CEL validationconfig/crd/bases/apisix.apache.org_apisixroutes.yaml: regenerateddocs/en/latest/reference/api-reference.md: regeneratedtest/e2e/crds/v2/route.go: e2e tests for urlencoded form field and JSON nested path matchingTesting
Unit tests:
E2e tests added:
Test ApisixRoute match by body vars (urlencoded): POST form fieldaction=loginTest ApisixRoute match by body vars (JSON nested path): POST JSON{"model": {"version": "gpt-4"}}withmodel.versiondot-notation