Skip to content

Commit

Permalink
Find matched api in enforcer
Browse files Browse the repository at this point in the history
  • Loading branch information
AmaliMatharaarachchi committed Sep 24, 2024
1 parent 20c3dc8 commit 1102e8f
Show file tree
Hide file tree
Showing 39 changed files with 837 additions and 268 deletions.
1 change: 1 addition & 0 deletions adapter/api/proto/wso2/discovery/api/Resource.proto
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@ message Operation {
string tier = 3;
OperationPolicies policies = 4;
repeated string scopes = 5;
string matchID = 6;
// MockedApiConfig mockedApiConfig = 6;
}

Expand Down
1 change: 1 addition & 0 deletions adapter/api/proto/wso2/discovery/api/api.proto
Original file line number Diff line number Diff line change
Expand Up @@ -53,6 +53,7 @@ message Api {
string mutualSSL = 15;
map<string, bool> applicationSecurity = 16;
bool transportSecurity = 17;
repeated string httpRouteIDs = 19;
/// string graphQLSchema = 22;
repeated GraphqlComplexity graphqlComplexityInfo = 23;
bool systemAPI = 24;
Expand Down
2 changes: 2 additions & 0 deletions adapter/api/proto/wso2/discovery/config/enforcer/config.proto
Original file line number Diff line number Diff line change
Expand Up @@ -53,4 +53,6 @@ message Config {

bool mandateInternalKeyValidation = 15;

bool enableGatewayClassController = 16;

}
2 changes: 2 additions & 0 deletions adapter/config/default_config.go
Original file line number Diff line number Diff line change
Expand Up @@ -290,6 +290,8 @@ var defaultConfig = &Config{
CommonControllerXDSPort: "18002",
CommonControllerRestPort: "18003",
EnforcerLabel: "wso2-apk-default",
EnforcerImage: "wso2/apk-enforcer:1.1.0",
EnforcerImagePullPolicy: "Always",
EnforcerRegion: "UNKNOWN",
EnforcerXDSMaxMsgSize: "4194304",
EnforcerXDSMaxRetries: "3",
Expand Down
2 changes: 2 additions & 0 deletions adapter/config/types.go
Original file line number Diff line number Diff line change
Expand Up @@ -336,6 +336,8 @@ type gateway struct {
CommonControllerRestPort string
EnforcerLabel string
EnforcerRegion string
EnforcerImage string
EnforcerImagePullPolicy string
EnforcerXDSMaxMsgSize string
EnforcerXDSMaxRetries string
JavaOpts string
Expand Down
2 changes: 2 additions & 0 deletions adapter/internal/discovery/xds/marshaller.go
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,7 @@ func MarshalConfig(config *config.Config) *enforcer.Config {
}
mandateSubscriptionValidation := config.Enforcer.MandateSubscriptionValidation
mandateInternalKeyValidation := config.Enforcer.MandateInternalKeyValidation
enableGatewayClassController := config.Adapter.EnableGatewayClassController

analytics := &enforcer.Analytics{
Enabled: config.Analytics.Enabled,
Expand Down Expand Up @@ -160,6 +161,7 @@ func MarshalConfig(config *config.Config) *enforcer.Config {
Soap: soap,
MandateSubscriptionValidation: mandateSubscriptionValidation,
MandateInternalKeyValidation: mandateInternalKeyValidation,
EnableGatewayClassController: enableGatewayClassController,
HttpClient: httpClient,
}
}
Expand Down
2 changes: 2 additions & 0 deletions adapter/internal/oasparser/config_generator.go
Original file line number Diff line number Diff line change
Expand Up @@ -241,6 +241,7 @@ func GetEnforcerAPI(adapterInternalAPI *model.AdapterInternalAPI, vhost string)
}
return nil
}(),
HttpRouteIDs: adapterInternalAPI.HTTPRouteIDs,
}
}

Expand All @@ -263,6 +264,7 @@ func GetEnforcerAPIOperation(operation model.Operation, isMockedAPI bool) *api.O
ApiAuthentication: castAPIAuthenticationsToEnforcerAPIAuthentications(operation.GetAuthentication()),
Tier: operation.GetTier(),
Policies: policies,
MatchID: operation.GetMatchID(),
// MockedApiConfig: mockedAPIConfig,
}
return &apiOperation
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -72,7 +72,7 @@ func TestCreateRoute(t *testing.T) {
})

resourceWithGet := model.CreateMinimalDummyResourceForTests("/xWso2BasePath/resourcePath",
[]*model.Operation{model.NewOperationWithPolicies("GET", policies)},
[]*model.Operation{model.NewOperationWithPolicies("GET", policies, "")},
"resource_operation_id", []model.Endpoint{endpoint}, true, false)
clusterName := "resource_operation_id"
hostRewriteSpecifier := &routev3.RouteAction_AutoHostRewrite{
Expand Down Expand Up @@ -142,7 +142,7 @@ func TestCreateRouteClusterSpecifier(t *testing.T) {
Port: 80,
RawURL: "http://abc.com",
}
resourceWithGet := model.CreateMinimalDummyResourceForTests("/resourcePath", []*model.Operation{model.NewOperation("GET", nil, nil)},
resourceWithGet := model.CreateMinimalDummyResourceForTests("/resourcePath", []*model.Operation{model.NewOperation("GET", nil, nil, "")},
"resource_operation_id", []model.Endpoint{endpoint}, false, false)

route, err := createRoutes(generateRouteCreateParamsForUnitTests(title, apiType, vHost, xWso2BasePath, version, endpointBasePath,
Expand Down Expand Up @@ -173,7 +173,7 @@ func TestCreateRouteExtAuthzContext(t *testing.T) {
Port: 80,
RawURL: "http://abc.com",
}
resourceWithGet := model.CreateMinimalDummyResourceForTests("/resourcePath", []*model.Operation{model.NewOperation("GET", nil, nil)},
resourceWithGet := model.CreateMinimalDummyResourceForTests("/resourcePath", []*model.Operation{model.NewOperation("GET", nil, nil, "")},
"resource_operation_id", []model.Endpoint{endpoint}, false, false)

route, err := createRoutes(generateRouteCreateParamsForUnitTests(title, apiType, vHost, xWso2BasePath, version,
Expand Down Expand Up @@ -570,7 +570,7 @@ func TestGetCorsPolicy(t *testing.T) {
"Cors Allowed Origin Header mismatch")
assert.Empty(t, corsPolicy3.GetAllowCredentials(), "Allow Credential property should not be assigned.")

resourceWithGet := model.CreateMinimalDummyResourceForTests("/resourcePath", []*model.Operation{model.NewOperation("GET", nil, nil)},
resourceWithGet := model.CreateMinimalDummyResourceForTests("/resourcePath", []*model.Operation{model.NewOperation("GET", nil, nil, "")},
"resource_operation_id", []model.Endpoint{endpoint}, false, false)

// Route without CORS configuration
Expand Down
6 changes: 3 additions & 3 deletions adapter/internal/oasparser/envoyconf/listener_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -196,9 +196,9 @@ func testCreateRoutesForUnitTests(t *testing.T) []*routev3.Route {
RawURL: "http://abc.com",
}

operationGet := model.NewOperation("GET", nil, nil)
operationPost := model.NewOperation("POST", nil, nil)
operationPut := model.NewOperation("PUT", nil, nil)
operationGet := model.NewOperation("GET", nil, nil, "")
operationPost := model.NewOperation("POST", nil, nil, "")
operationPut := model.NewOperation("PUT", nil, nil, "")
resourceWithGet := model.CreateMinimalDummyResourceForTests("/resourcePath", []*model.Operation{operationGet},
"resource_operation_id", []model.Endpoint{endpoint}, false, false)
resourceWithPost := model.CreateMinimalDummyResourceForTests("/resourcePath", []*model.Operation{operationPost},
Expand Down
4 changes: 2 additions & 2 deletions adapter/internal/oasparser/envoyconf/routes_with_clusters.go
Original file line number Diff line number Diff line change
Expand Up @@ -178,7 +178,7 @@ func CreateRoutesWithClusters(adapterInternalAPI *model.AdapterInternalAPI, inte
},
},
}
gqlop := model.NewOperationWithPolicies("POST", policies)
gqlop := model.NewOperationWithPolicies("POST", policies, "")
resource := model.CreateMinimalResource(adapterInternalAPI.GetXWso2Basepath(), []*model.Operation{gqlop}, "", adapterInternalAPI.Endpoints, true, false, gwapiv1.PathMatchExact)
routesP, err := createRoutes(genRouteCreateParams(adapterInternalAPI, &resource, vHost, basePath, clusterName, nil,
nil, organizationID, false, false, nil))
Expand Down Expand Up @@ -1074,7 +1074,7 @@ func createRoutes(params *routeCreateParams) (routes []*routev3.Route, err error
}
}
if !hasOptions {
operations = append(operations, model.NewOperation("OPTIONS", nil, nil))
operations = append(operations, model.NewOperation("OPTIONS", nil, nil, ""))
}
}

Expand Down
11 changes: 8 additions & 3 deletions adapter/internal/oasparser/model/adapter_internal_api.go
Original file line number Diff line number Diff line change
Expand Up @@ -82,6 +82,7 @@ type AdapterInternalAPI struct {
Endpoints *EndpointCluster
EndpointSecurity []*EndpointSecurity
AIProvider InternalAIProvider
HTTPRouteIDs []string
}

// BackendJWTTokenInfo represents the object structure holding the information related to the JWT Generator
Expand Down Expand Up @@ -889,7 +890,11 @@ func (adapterInternalAPI *AdapterInternalAPI) SetInfoHTTPRouteCR(httpRoute *gwap
loggers.LoggerOasparser.Debugf("Calculating auths for API ..., API_UUID = %v", adapterInternalAPI.UUID)
apiAuth := getSecurity(resourceAuthScheme)

for _, match := range rule.Matches {
if !hasRequestRedirectPolicy && len(rule.BackendRefs) < 1 {
return fmt.Errorf("no backendref were provided")
}

for matchID, match := range rule.Matches {
if hasURLRewritePolicy && hasRequestRedirectPolicy {
return fmt.Errorf("cannot have URL Rewrite and Request Redirect under the same rule")
}
Expand All @@ -909,8 +914,8 @@ func (adapterInternalAPI *AdapterInternalAPI) SetInfoHTTPRouteCR(httpRoute *gwap
})
}
resourcePath := adapterInternalAPI.xWso2Basepath + *match.Path.Value

operations := getAllowedOperations(match.Method, policies, apiAuth,
matchID := getMatchID(httpRoute.Namespace, httpRoute.Name, ruleID, matchID)
operations := getAllowedOperations(matchID, match.Method, policies, apiAuth,
parseRateLimitPolicyToInternal(resourceRatelimitPolicy), scopes, mirrorEndpointClusters)

resource := &Resource{
Expand Down
13 changes: 9 additions & 4 deletions adapter/internal/oasparser/model/api_operation.go
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,7 @@ type Operation struct {
mockedAPIConfig *api.MockedApiConfig
rateLimitPolicy *RateLimitPolicy
mirrorEndpointClusters []*EndpointCluster
matchID string
}

// Authentication holds authentication related configurations
Expand Down Expand Up @@ -109,6 +110,10 @@ func (operation *Operation) GetTier() string {
return operation.tier
}

func (operation *Operation) GetMatchID() string {
return operation.matchID
}

// GetMockedAPIConfig returns the operation level mocked API implementation configs
func (operation *Operation) GetMockedAPIConfig() *api.MockedApiConfig {
return operation.mockedAPIConfig
Expand Down Expand Up @@ -176,14 +181,14 @@ func (operation *Operation) GetCallInterceptorService(isIn bool) InterceptEndpoi
}

// NewOperation Creates and returns operation type object
func NewOperation(method string, security []string, extensions map[string]interface{}) *Operation {
func NewOperation(method string, security []string, extensions map[string]interface{}, matchID string) *Operation {
tier := ResolveThrottlingTier(extensions)
disableSecurity := ResolveDisableSecurity(extensions)
id := uuid.New().String()
return &Operation{id, method, security, nil, tier, disableSecurity, extensions, OperationPolicies{}, &api.MockedApiConfig{}, nil, nil}
return &Operation{id, method, security, nil, tier, disableSecurity, extensions, OperationPolicies{}, &api.MockedApiConfig{}, nil, nil, matchID}
}

// NewOperationWithPolicies Creates and returns operation with given method and policies
func NewOperationWithPolicies(method string, policies OperationPolicies) *Operation {
return &Operation{iD: uuid.New().String(), method: method, policies: policies}
func NewOperationWithPolicies(method string, policies OperationPolicies, matchID string) *Operation {
return &Operation{iD: uuid.New().String(), method: method, policies: policies, matchID: matchID}
}
9 changes: 9 additions & 0 deletions adapter/internal/oasparser/model/common.go
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ package model

import (
"errors"
"fmt"
"net/url"
"regexp"
"strconv"
Expand Down Expand Up @@ -155,3 +156,11 @@ func getHostandBasepathandPort(apiType string, rawURL string) (*Endpoint, error)

return &Endpoint{Host: host, Basepath: basepath, Port: port, URLType: urlType, RawURL: rawURL}, nil
}

func getRouteID(namespace, name string) string {
return fmt.Sprintf("httproute/%s/%s/", namespace, name)
}

func getMatchID(namespace, name string, ruleID, matchID int) string {
return fmt.Sprintf("%srule/%d/match/%d", getRouteID(namespace, name), ruleID, matchID)
}
30 changes: 21 additions & 9 deletions adapter/internal/oasparser/model/http_route.go
Original file line number Diff line number Diff line change
Expand Up @@ -287,26 +287,26 @@ func getSecurity(authScheme *dpv1alpha2.Authentication) *Authentication {
}

// getAllowedOperations retuns a list of allowed operatons, if httpMethod is not specified then all methods are allowed.
func getAllowedOperations(httpMethod *gwapiv1.HTTPMethod, policies OperationPolicies, auth *Authentication,
func getAllowedOperations(matchID string, httpMethod *gwapiv1.HTTPMethod, policies OperationPolicies, auth *Authentication,
ratelimitPolicy *RateLimitPolicy, scopes []string, mirrorEndpointClusters []*EndpointCluster) []*Operation {
if httpMethod != nil {
return []*Operation{{iD: uuid.New().String(), method: string(*httpMethod), policies: policies,
auth: auth, rateLimitPolicy: ratelimitPolicy, scopes: scopes, mirrorEndpointClusters: mirrorEndpointClusters}}
auth: auth, rateLimitPolicy: ratelimitPolicy, scopes: scopes, mirrorEndpointClusters: mirrorEndpointClusters, matchID: matchID}}
}
return []*Operation{{iD: uuid.New().String(), method: string(gwapiv1.HTTPMethodGet), policies: policies,
auth: auth, rateLimitPolicy: ratelimitPolicy, scopes: scopes},
auth: auth, rateLimitPolicy: ratelimitPolicy, scopes: scopes, matchID: matchID},
{iD: uuid.New().String(), method: string(gwapiv1.HTTPMethodPost), policies: policies,
auth: auth, rateLimitPolicy: ratelimitPolicy, scopes: scopes, mirrorEndpointClusters: mirrorEndpointClusters},
auth: auth, rateLimitPolicy: ratelimitPolicy, scopes: scopes, mirrorEndpointClusters: mirrorEndpointClusters, matchID: matchID},
{iD: uuid.New().String(), method: string(gwapiv1.HTTPMethodDelete), policies: policies,
auth: auth, rateLimitPolicy: ratelimitPolicy, scopes: scopes, mirrorEndpointClusters: mirrorEndpointClusters},
auth: auth, rateLimitPolicy: ratelimitPolicy, scopes: scopes, mirrorEndpointClusters: mirrorEndpointClusters, matchID: matchID},
{iD: uuid.New().String(), method: string(gwapiv1.HTTPMethodPatch), policies: policies,
auth: auth, rateLimitPolicy: ratelimitPolicy, scopes: scopes, mirrorEndpointClusters: mirrorEndpointClusters},
auth: auth, rateLimitPolicy: ratelimitPolicy, scopes: scopes, mirrorEndpointClusters: mirrorEndpointClusters, matchID: matchID},
{iD: uuid.New().String(), method: string(gwapiv1.HTTPMethodPut), policies: policies,
auth: auth, rateLimitPolicy: ratelimitPolicy, scopes: scopes, mirrorEndpointClusters: mirrorEndpointClusters},
auth: auth, rateLimitPolicy: ratelimitPolicy, scopes: scopes, mirrorEndpointClusters: mirrorEndpointClusters, matchID: matchID},
{iD: uuid.New().String(), method: string(gwapiv1.HTTPMethodHead), policies: policies,
auth: auth, rateLimitPolicy: ratelimitPolicy, scopes: scopes, mirrorEndpointClusters: mirrorEndpointClusters},
auth: auth, rateLimitPolicy: ratelimitPolicy, scopes: scopes, mirrorEndpointClusters: mirrorEndpointClusters, matchID: matchID},
{iD: uuid.New().String(), method: string(gwapiv1.HTTPMethodOptions), policies: policies,
auth: auth, rateLimitPolicy: ratelimitPolicy, scopes: scopes, mirrorEndpointClusters: mirrorEndpointClusters}}
auth: auth, rateLimitPolicy: ratelimitPolicy, scopes: scopes, mirrorEndpointClusters: mirrorEndpointClusters, matchID: matchID}}
}

// SetInfoAPICR populates ID, ApiType, Version and XWso2BasePath of adapterInternalAPI.
Expand All @@ -319,4 +319,16 @@ func (swagger *AdapterInternalAPI) SetInfoAPICR(api dpv1alpha3.API) {
swagger.OrganizationID = api.Spec.Organization
swagger.IsSystemAPI = api.Spec.SystemAPI
swagger.APIProperties = api.Spec.APIProperties
httpRouteIDs := []string{}
for _, route := range api.Spec.Production {
for _, routeRef := range route.RouteRefs {
httpRouteIDs = append(httpRouteIDs, getRouteID(api.Namespace, routeRef))
}
}
for _, route := range api.Spec.Sandbox {
for _, routeRef := range route.RouteRefs {
httpRouteIDs = append(httpRouteIDs, getRouteID(api.Namespace, routeRef))
}
}
swagger.HTTPRouteIDs = httpRouteIDs
}
Original file line number Diff line number Diff line change
Expand Up @@ -272,11 +272,9 @@ func expectedProxyContainers(infra *ir.ProxyInfra,
},
},
{
Name: enforcerContainerName,
Image: *deploymentConfig.EnforcerContainer.Image,
ImagePullPolicy: corev1.PullIfNotPresent,
// Command: []string{"envoy"},
// Args: args,
Name: enforcerContainerName,
Image: *deploymentConfig.EnforcerContainer.Image,
ImagePullPolicy: corev1.PullPolicy(config.ReadConfigs().Deployment.Gateway.EnforcerImagePullPolicy),
Env: expectedEnforcerEnv(deploymentConfig.EnforcerContainer),
Resources: *deploymentConfig.EnforcerContainer.Resources,
SecurityContext: deploymentConfig.EnforcerContainer.SecurityContext,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ import (
"sort"
"strings"

"github.com/wso2/apk/adapter/config"
autoscalingv2 "k8s.io/api/autoscaling/v2"
v1 "k8s.io/api/core/v1"
"k8s.io/apimachinery/pkg/api/resource"
Expand Down Expand Up @@ -54,7 +55,7 @@ func (e *EnvoyProxy) GetEnvoyProxyProvider() *EnvoyProxyProvider {
// DefaultEnvoyProxyKubeProvider returns a new EnvoyProxyKubernetesProvider with default settings.
func DefaultEnvoyProxyKubeProvider() *EnvoyProxyKubernetesProvider {
return &EnvoyProxyKubernetesProvider{
EnvoyDeployment: DefaultKubernetesDeployment(DefaultEnvoyProxyImage, DefaultEnforcerImage),
EnvoyDeployment: DefaultKubernetesDeployment(DefaultEnvoyProxyImage, config.ReadConfigs().Deployment.Gateway.EnforcerImage),
EnvoyService: DefaultKubernetesService(),
}
}
Expand Down Expand Up @@ -88,10 +89,10 @@ func (r *EnvoyProxyProvider) GetEnvoyProxyKubeProvider() *EnvoyProxyKubernetesPr
}

if r.Kubernetes.EnvoyDeployment == nil {
r.Kubernetes.EnvoyDeployment = DefaultKubernetesDeployment(DefaultEnvoyProxyImage, DefaultEnforcerImage)
r.Kubernetes.EnvoyDeployment = DefaultKubernetesDeployment(DefaultEnvoyProxyImage, config.ReadConfigs().Deployment.Gateway.EnforcerImage)
}

r.Kubernetes.EnvoyDeployment.defaultKubernetesDeploymentSpec(DefaultEnvoyProxyImage, DefaultEnforcerImage)
r.Kubernetes.EnvoyDeployment.defaultKubernetesDeploymentSpec(DefaultEnvoyProxyImage, config.ReadConfigs().Deployment.Gateway.EnforcerImage)

if r.Kubernetes.EnvoyService == nil {
r.Kubernetes.EnvoyService = DefaultKubernetesService()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -38,8 +38,6 @@ const (
DefaultDeploymentMemoryResourceRequests = "512Mi"
// DefaultEnvoyProxyImage is the default image used by envoyproxy
DefaultEnvoyProxyImage = "envoyproxy/envoy:distroless-v1.29.3"
// DefaultEnforcerImage default image used by enforcer
DefaultEnforcerImage = "wso2/apk-enforcer:1.1.0"
// DefaultShutdownManagerCPUResourceRequests for shutdown manager cpu resource
DefaultShutdownManagerCPUResourceRequests = "10m"
// DefaultShutdownManagerMemoryResourceRequests for shutdown manager memory resource
Expand Down
3 changes: 2 additions & 1 deletion adapter/internal/operator/gateway-api/version/version.go
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ import (
"runtime/debug"
"strings"

"github.com/wso2/apk/adapter/config"
"github.com/wso2/apk/adapter/internal/operator/gateway-api/v1alpha1"
"sigs.k8s.io/yaml"
)
Expand Down Expand Up @@ -57,7 +58,7 @@ var (
envoyGatewayVersion string
gatewayAPIVersion string
envoyProxyVersion = strings.Split(v1alpha1.DefaultEnvoyProxyImage, ":")[1]
enforcerVersion = strings.Split(v1alpha1.DefaultEnforcerImage, ":")[1]
enforcerVersion = strings.Split(config.ReadConfigs().Deployment.Gateway.EnforcerImage, ":")[1]
shutdownManagerVersion string
gitCommitID string
)
Expand Down
Loading

0 comments on commit 1102e8f

Please sign in to comment.