Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: correctly handle route schema defaults with Konnect #55

Merged
merged 1 commit into from
Feb 7, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 26 additions & 0 deletions pkg/file/builder.go
Original file line number Diff line number Diff line change
Expand Up @@ -1110,11 +1110,37 @@ func (b *stateBuilder) ingestRoute(r FRoute) error {
return err
}
r.Route.StripPath = stripPath

hasExpression := r.Route.Expression != nil
hasRegexPriority := r.Route.RegexPriority != nil
hasPathHandling := r.Route.PathHandling != nil

b.defaulter.MustSet(&r.Route)
if route != nil {
r.Route.CreatedAt = route.CreatedAt
}

// Kong Gateway supports different schemas for different router versions.
// On the other hand, Konnect can support only one schema including all
// fields from 'traditional' and 'expressions' router schemas.
// This may be problematic when it comes to defaults injection, because
// the defaults for the 'traditiona' router schema can be wrongly injected
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

traditiona -> traditional 🙃

// into the 'expressions' route configuration.
//
// Here we make sure that only the fields that are supported for a given
// router version are set in the route configuration.
if b.isKonnect && hasExpression && !(hasRegexPriority || hasPathHandling) {
if r.Route.PathHandling != nil {
r.Route.PathHandling = nil
}
if r.Route.RegexPriority != nil {
r.Route.RegexPriority = nil
}
if r.Route.Priority == nil {
r.Route.Priority = kong.Uint64(0)
}
}

b.rawState.Routes = append(b.rawState.Routes, &r.Route)
err = b.intermediate.Routes.Add(state.Route{Route: r.Route})
if err != nil {
Expand Down
90 changes: 90 additions & 0 deletions pkg/file/builder_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -2755,3 +2755,93 @@ func Test_getStripPathBasedOnProtocols(t *testing.T) {
})
}
}

func Test_stateBuilder_ingestRouteKonnect(t *testing.T) {
assert := assert.New(t)
rand.Seed(42)
type fields struct {
currentState *state.KongState
}
type args struct {
route FRoute
}
tests := []struct {
name string
fields fields
args args
wantErr bool
wantState *utils.KongRawState
}{
{
name: "traditional route",
fields: fields{
currentState: emptyState(),
},
args: args{
route: FRoute{
Route: kong.Route{
Name: kong.String("foo"),
},
},
},
wantErr: false,
wantState: &utils.KongRawState{
Routes: []*kong.Route{
{
ID: kong.String("538c7f96-b164-4f1b-97bb-9f4bb472e89f"),
Name: kong.String("foo"),
PreserveHost: kong.Bool(false),
RegexPriority: kong.Int(0),
StripPath: kong.Bool(false),
Protocols: kong.StringSlice("http", "https"),
},
},
},
},
{
name: "expression route",
fields: fields{
currentState: emptyState(),
},
args: args{
route: FRoute{
Route: kong.Route{
Name: kong.String("foo"),
Expression: kong.String(`'(http.path == "/test") || (http.path ^= "/test/")'`),
},
},
},
wantErr: false,
wantState: &utils.KongRawState{
Routes: []*kong.Route{
{
ID: kong.String("5b1484f2-5209-49d9-b43e-92ba09dd9d52"),
Name: kong.String("foo"),
PreserveHost: kong.Bool(false),
Expression: kong.String(`'(http.path == "/test") || (http.path ^= "/test/")'`),
Priority: kong.Uint64(0),
StripPath: kong.Bool(false),
Protocols: kong.StringSlice("http", "https"),
},
},
},
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
ctx := context.Background()
b := &stateBuilder{
currentState: tt.fields.currentState,
isKonnect: true,
}
b.rawState = &utils.KongRawState{}
d, _ := utils.GetDefaulter(ctx, defaulterTestOpts)
b.defaulter = d
b.intermediate, _ = state.NewKongState()
Comment on lines +2838 to +2840
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Too late to the party but any particular reason not to check the errors here?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

could be done, but not meaningful for the specific test...copy&pasta mistake

if err := b.ingestRoute(tt.args.route); (err != nil) != tt.wantErr {
t.Errorf("stateBuilder.ingestRoute() error = %v, wantErr %v", err, tt.wantErr)
}
assert.Equal(tt.wantState, b.rawState)
})
}
}
Loading