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

Net 5875 - Create the Exported Services Resources #19117

Merged
merged 88 commits into from
Oct 26, 2023
Merged
Show file tree
Hide file tree
Changes from 16 commits
Commits
Show all changes
88 commits
Select commit Hold shift + click to select a range
714f8a3
init
absolutelightning Oct 9, 2023
c1e1e4e
computed exported service
absolutelightning Oct 9, 2023
8be5941
make proto
absolutelightning Oct 9, 2023
f7f396e
exported services resource
absolutelightning Oct 9, 2023
55ba121
exported services test
absolutelightning Oct 9, 2023
755b08d
added some tests and namespace exported service
absolutelightning Oct 9, 2023
10af828
partition exported services
absolutelightning Oct 9, 2023
c97f8c2
computed service
absolutelightning Oct 9, 2023
074ed36
computed services tests
absolutelightning Oct 9, 2023
4221562
register types
absolutelightning Oct 9, 2023
7415265
fix comment
absolutelightning Oct 9, 2023
75e2b49
Merge branch 'main' into NET-5875
absolutelightning Oct 9, 2023
689de78
make proto lint
absolutelightning Oct 9, 2023
5375a1a
fix proto format make proto
absolutelightning Oct 9, 2023
e15f0eb
Merge branch 'NET-5875' of ssh://github.com/hashicorp/consul into NET…
absolutelightning Oct 9, 2023
13e59ff
make codegen
absolutelightning Oct 9, 2023
a681ded
Update proto-public/pbmulticluster/v1alpha1/computed_exported_service…
absolutelightning Oct 10, 2023
ff6a831
Update internal/multicluster/internal/types/computed_exported_service…
absolutelightning Oct 10, 2023
f2a7e22
using different way of resource creation in tests
absolutelightning Oct 10, 2023
13a5ed0
make proto
absolutelightning Oct 10, 2023
2e21983
Merge branch 'main' into NET-5875
absolutelightning Oct 10, 2023
6cfa2a0
fix computed exported services test
absolutelightning Oct 11, 2023
d12e785
fix tests
absolutelightning Oct 11, 2023
3df55fb
differnet validation for computed services for ent and ce
absolutelightning Oct 11, 2023
e1a8e96
Acls for exported services
absolutelightning Oct 11, 2023
8a922ae
added validations for enterprise features in ce
absolutelightning Oct 11, 2023
bbb7592
fix error
absolutelightning Oct 11, 2023
08d9d6e
fix acls test
absolutelightning Oct 11, 2023
393e5eb
Update internal/multicluster/internal/types/validation_exported_servi…
absolutelightning Oct 12, 2023
59cb443
removed the create method
absolutelightning Oct 12, 2023
15febaf
update proto
absolutelightning Oct 12, 2023
9d5e2da
removed namespace
absolutelightning Oct 12, 2023
437490b
created seperate function for ce and ent
absolutelightning Oct 13, 2023
d97bfd8
test files updated and validations fixed
absolutelightning Oct 13, 2023
2985849
added nil checks
absolutelightning Oct 13, 2023
2103241
fix tests
absolutelightning Oct 13, 2023
5c1ef95
added comments
absolutelightning Oct 13, 2023
792e493
removed tenancy check
absolutelightning Oct 16, 2023
9a6f4b6
added mutation function
absolutelightning Oct 16, 2023
022be04
fix mutation method
absolutelightning Oct 16, 2023
c0757c8
fix list permissions in test
absolutelightning Oct 16, 2023
617b297
fix pr comments
absolutelightning Oct 16, 2023
a9202a6
fix tests
absolutelightning Oct 17, 2023
63aa314
lisence
absolutelightning Oct 17, 2023
9ff14cc
busl license
absolutelightning Oct 17, 2023
c7469ca
Merge branch 'main' into NET-5875
absolutelightning Oct 17, 2023
f78152f
Merge branch 'main' into NET-5875
absolutelightning Oct 18, 2023
79eda17
Update internal/multicluster/internal/types/helpers_ce.go
absolutelightning Oct 19, 2023
25d0993
Update internal/multicluster/internal/types/helpers_ce.go
absolutelightning Oct 19, 2023
d48c01e
Update internal/multicluster/internal/types/helpers_ce.go
absolutelightning Oct 19, 2023
c44b424
make proto
absolutelightning Oct 19, 2023
e6bb0db
Merge branch 'NET-5875' of ssh://github.com/hashicorp/consul into NET…
absolutelightning Oct 19, 2023
fc29782
some pr comments addressed
absolutelightning Oct 19, 2023
20e5781
some pr comments addressed
absolutelightning Oct 19, 2023
d729d59
acls helper
absolutelightning Oct 19, 2023
1c4cf98
Merge branch 'main' of ssh://github.com/hashicorp/consul into NET-5875
absolutelightning Oct 19, 2023
112ad62
Merge branch 'main' into NET-5875
absolutelightning Oct 20, 2023
7732609
some comment changes
absolutelightning Oct 23, 2023
82c0ddb
Merge branch 'NET-5875' of ssh://github.com/hashicorp/consul into NET…
absolutelightning Oct 23, 2023
5308961
removed unused files
absolutelightning Oct 23, 2023
d091b46
fixes
absolutelightning Oct 23, 2023
b4d0247
fix function in file
absolutelightning Oct 23, 2023
e6380c2
caps
absolutelightning Oct 23, 2023
07f3932
Merge branch 'main' into NET-5875
absolutelightning Oct 23, 2023
e2b2052
Merge branch 'NET-5875' of ssh://github.com/hashicorp/consul into NET…
absolutelightning Oct 23, 2023
5f9589e
some positioing
absolutelightning Oct 23, 2023
d51bbdf
added test for validation error
absolutelightning Oct 23, 2023
e84e237
fix names
absolutelightning Oct 23, 2023
1c7efd8
made valid a function
absolutelightning Oct 23, 2023
e2e379b
remvoed patch
absolutelightning Oct 23, 2023
d982a03
Merge branch 'main' into NET-5875
absolutelightning Oct 23, 2023
3aac88d
removed mutations
absolutelightning Oct 23, 2023
678b311
Merge branch 'NET-5875' of ssh://github.com/hashicorp/consul into NET…
absolutelightning Oct 23, 2023
c6ea870
v2 beta1
absolutelightning Oct 23, 2023
999dd6f
v2beta1
absolutelightning Oct 23, 2023
3b37a0a
rmeoved v1alpha1
absolutelightning Oct 23, 2023
732e2ca
validate error
absolutelightning Oct 24, 2023
add5b45
Merge branch 'main' into NET-5875
absolutelightning Oct 24, 2023
cd29bed
Merge branch 'NET-5875' of ssh://github.com/hashicorp/consul into NET…
absolutelightning Oct 24, 2023
11fd797
Merge branch 'main' of ssh://github.com/hashicorp/consul into NET-5875
absolutelightning Oct 25, 2023
a11ad98
merge ent
absolutelightning Oct 25, 2023
d5a4ccc
some nits
absolutelightning Oct 26, 2023
a837887
Merge branch 'main' into NET-5875
absolutelightning Oct 26, 2023
00984f1
removed dup func
absolutelightning Oct 26, 2023
5407a04
Merge branch 'NET-5875' of ssh://github.com/hashicorp/consul into NET…
absolutelightning Oct 26, 2023
4f963f0
removed nil check
absolutelightning Oct 26, 2023
b15d668
Merge branch 'main' into NET-5875
absolutelightning Oct 26, 2023
d1892da
Merge branch 'NET-5875' of ssh://github.com/hashicorp/consul into NET…
absolutelightning Oct 26, 2023
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
2 changes: 2 additions & 0 deletions agent/consul/type_registry.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import (
"github.com/hashicorp/consul/internal/auth"
"github.com/hashicorp/consul/internal/catalog"
"github.com/hashicorp/consul/internal/mesh"
"github.com/hashicorp/consul/internal/multicluster"
"github.com/hashicorp/consul/internal/resource"
"github.com/hashicorp/consul/internal/resource/demo"
"github.com/hashicorp/consul/internal/tenancy"
Expand All @@ -27,6 +28,7 @@ func NewTypeRegistry() resource.Registry {
catalog.RegisterTypes(registry)
auth.RegisterTypes(registry)
tenancy.RegisterTypes(registry)
multicluster.RegisterTypes(registry)

return registry
}
22 changes: 22 additions & 0 deletions internal/multicluster/exports.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
// Copyright (c) HashiCorp, Inc.
// SPDX-License-Identifier: BUSL-1.1

package multicluster

import (
"github.com/hashicorp/consul/internal/multicluster/internal/types"
"github.com/hashicorp/consul/internal/resource"
)

var (
// API Group Information
APIGroup = types.GroupName
VersionV1Alpha1 = types.VersionV1Alpha1
CurrentVersion = types.CurrentVersion
)

// RegisterTypes adds all resource types within the "multicluster" API group
// to the given type registry
func RegisterTypes(r resource.Registry) {
types.Register(r)
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
// Copyright (c) HashiCorp, Inc.
// SPDX-License-Identifier: BUSL-1.1

package types

import (
"fmt"
"github.com/hashicorp/consul/acl"
"github.com/hashicorp/consul/internal/resource"
pbmulticluster "github.com/hashicorp/consul/proto-public/pbmulticluster/v1alpha1"
"github.com/hashicorp/consul/proto-public/pbresource"
"github.com/hashicorp/go-multierror"
)

const (
ComputedExportedServicesName = "global"
)

func RegisterComputedExportedServices(r resource.Registry) {
r.Register(resource.Registration{
Type: pbmulticluster.ComputedExportedServicesType,
Proto: &pbmulticluster.ComputedExportedServices{},
Scope: resource.ScopePartition,
Validate: ValidateComputedExportedServices,
ACLs: &resource.ACLHooks{
Read: aclReadHookComputedExportedServices,
Write: aclWriteHookComputedExportedServices,
List: aclListHookComputedExportedServices,
},
})
}

func ValidateComputedExportedServices(res *pbresource.Resource) error {
absolutelightning marked this conversation as resolved.
Show resolved Hide resolved
var computedExportedServices pbmulticluster.ComputedExportedServices

if err := res.Data.UnmarshalTo(&computedExportedServices); err != nil {
return resource.NewErrDataParse(&computedExportedServices, err)
}

var merr error

if res.Id.Name != ComputedExportedServicesName {
merr = multierror.Append(merr, resource.ErrInvalidField{
Name: "name",
Wrapped: fmt.Errorf("name can only be \"global\""),
})
}
return merr
}

func aclReadHookComputedExportedServices(authorizer acl.Authorizer, authzContext *acl.AuthorizerContext, id *pbresource.ID, _ *pbresource.Resource) error {
return authorizer.ToAllowAuthorizer().MeshReadAllowed(authzContext)
}

func aclWriteHookComputedExportedServices(authorizer acl.Authorizer, authzContext *acl.AuthorizerContext, res *pbresource.Resource) error {
return authorizer.ToAllowAuthorizer().MeshWriteAllowed(authzContext)
}

func aclListHookComputedExportedServices(authorizer acl.Authorizer, authzContext *acl.AuthorizerContext) error {
return nil
absolutelightning marked this conversation as resolved.
Show resolved Hide resolved
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,97 @@
// Copyright (c) HashiCorp, Inc.
// SPDX-License-Identifier: BUSL-1.1

package types

import (
"errors"
multiclusterv1alpha1 "github.com/hashicorp/consul/proto-public/pbmulticluster/v1alpha1"
"github.com/hashicorp/consul/proto-public/pbresource"
"github.com/stretchr/testify/require"
"google.golang.org/protobuf/reflect/protoreflect"
"google.golang.org/protobuf/types/known/anypb"
"testing"
)

func createComputedExportedServicesResource(t *testing.T, data protoreflect.ProtoMessage, name string) *pbresource.Resource {
absolutelightning marked this conversation as resolved.
Show resolved Hide resolved
res := &pbresource.Resource{
Id: &pbresource.ID{
Type: multiclusterv1alpha1.ComputedExportedServicesType,
Name: name,
},
}

var err error
res.Data, err = anypb.New(data)
require.NoError(t, err)
return res
absolutelightning marked this conversation as resolved.
Show resolved Hide resolved
}

func validComputedExportedServicesWithPeer() *multiclusterv1alpha1.ComputedExportedServices {
consumers := make([]*multiclusterv1alpha1.ComputedExportedService, 1)
consumers[0] = new(multiclusterv1alpha1.ComputedExportedService)
var computedExportedServicePeer *multiclusterv1alpha1.ComputedExportedServicesConsumer_Peer
computedExportedServicePeer = new(multiclusterv1alpha1.ComputedExportedServicesConsumer_Peer)
computedExportedServicePeer.Peer = "peer"
consumers[0].Consumers = []*multiclusterv1alpha1.ComputedExportedServicesConsumer{
{
ConsumerTenancy: computedExportedServicePeer,
},
}
absolutelightning marked this conversation as resolved.
Show resolved Hide resolved
return &multiclusterv1alpha1.ComputedExportedServices{
Consumers: consumers,
}
}

func validComputedExportedServicesWithPartition() *multiclusterv1alpha1.ComputedExportedServices {
consumers := make([]*multiclusterv1alpha1.ComputedExportedService, 1)
consumers[0] = new(multiclusterv1alpha1.ComputedExportedService)
var computedExportedServicePartition *multiclusterv1alpha1.ComputedExportedServicesConsumer_Partition
computedExportedServicePartition = new(multiclusterv1alpha1.ComputedExportedServicesConsumer_Partition)
computedExportedServicePartition.Partition = "partition"
consumers[0].Consumers = []*multiclusterv1alpha1.ComputedExportedServicesConsumer{
{
ConsumerTenancy: computedExportedServicePartition,
},
}
return &multiclusterv1alpha1.ComputedExportedServices{
Consumers: consumers,
}
}

func TestValidateComputedExportedServicesWithPeer_Ok(t *testing.T) {
res := createComputedExportedServicesResource(t, validComputedExportedServicesWithPeer(), ComputedExportedServicesName)

err := ValidateComputedExportedServices(res)
require.NoError(t, err)

var resDecoded multiclusterv1alpha1.ComputedExportedServices
err = res.Data.UnmarshalTo(&resDecoded)
require.NoError(t, err)
absolutelightning marked this conversation as resolved.
Show resolved Hide resolved
require.Equal(t, 1, len(resDecoded.Consumers))
require.Equal(t, 1, len(resDecoded.Consumers[0].Consumers))
require.Equal(t, "peer", resDecoded.Consumers[0].Consumers[0].GetPeer())
absolutelightning marked this conversation as resolved.
Show resolved Hide resolved
}

func TestValidateComputedExportedServicesWithPartition_Ok(t *testing.T) {
absolutelightning marked this conversation as resolved.
Show resolved Hide resolved
res := createComputedExportedServicesResource(t, validComputedExportedServicesWithPartition(), ComputedExportedServicesName)

err := ValidateComputedExportedServices(res)
require.NoError(t, err)

var resDecoded multiclusterv1alpha1.ComputedExportedServices
err = res.Data.UnmarshalTo(&resDecoded)
require.NoError(t, err)
require.Equal(t, 1, len(resDecoded.Consumers))
require.Equal(t, 1, len(resDecoded.Consumers[0].Consumers))
require.Equal(t, "partition", resDecoded.Consumers[0].Consumers[0].GetPartition())
}

func TestValidateComputedExportedServices_InvalidName(t *testing.T) {
res := createComputedExportedServicesResource(t, validComputedExportedServicesWithPartition(), "computed-service")

err := ValidateComputedExportedServices(res)
require.Error(t, err)
expectedError := errors.New("invalid \"name\" field: name can only be \"global\"")
require.ErrorAs(t, err, &expectedError)
}
61 changes: 61 additions & 0 deletions internal/multicluster/internal/types/exported_services.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
// Copyright (c) HashiCorp, Inc.
// SPDX-License-Identifier: BUSL-1.1

package types

import (
"fmt"
"github.com/hashicorp/consul/acl"
"github.com/hashicorp/consul/internal/resource"
pbmulticluster "github.com/hashicorp/consul/proto-public/pbmulticluster/v1alpha1"
"github.com/hashicorp/consul/proto-public/pbresource"
"github.com/hashicorp/go-multierror"
)

func RegisterExportedServices(r resource.Registry) {
r.Register(resource.Registration{
Type: pbmulticluster.ExportedServicesType,
Proto: &pbmulticluster.ExportedServices{},
Scope: resource.ScopeNamespace,
Validate: ValidateExportedServices,
ACLs: &resource.ACLHooks{
Read: aclReadHookExportedServices,
Write: aclWriteHookExportedServices,
List: aclListHookExportedServices,
},
})
}

func ValidateExportedServices(res *pbresource.Resource) error {
var exportedService pbmulticluster.ExportedServices
absolutelightning marked this conversation as resolved.
Show resolved Hide resolved

if err := res.Data.UnmarshalTo(&exportedService); err != nil {
return resource.NewErrDataParse(&exportedService, err)
}

var merr error

if exportedService.Services == nil || len(exportedService.Services) == 0 {
merr = multierror.Append(merr, resource.ErrInvalidField{
Name: "services",
Wrapped: fmt.Errorf("at least one service must be set"),
})
}
return merr
}

func aclReadHookExportedServices(authorizer acl.Authorizer, authzContext *acl.AuthorizerContext, id *pbresource.ID, _ *pbresource.Resource) error {
serviceName := id.Name
absolutelightning marked this conversation as resolved.
Show resolved Hide resolved

return authorizer.ToAllowAuthorizer().ServiceReadAllowed(serviceName, authzContext)
}

func aclWriteHookExportedServices(authorizer acl.Authorizer, authzContext *acl.AuthorizerContext, res *pbresource.Resource) error {
serviceName := res.Id.Name
absolutelightning marked this conversation as resolved.
Show resolved Hide resolved

return authorizer.ToAllowAuthorizer().ServiceWriteAllowed(serviceName, authzContext)
}

func aclListHookExportedServices(authorizer acl.Authorizer, authzContext *acl.AuthorizerContext) error {
return nil
}
110 changes: 110 additions & 0 deletions internal/multicluster/internal/types/exported_services_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,110 @@
// Copyright (c) HashiCorp, Inc.
// SPDX-License-Identifier: BUSL-1.1

package types

import (
"errors"
multiclusterv1alpha1 "github.com/hashicorp/consul/proto-public/pbmulticluster/v1alpha1"
"github.com/hashicorp/consul/proto-public/pbresource"
"github.com/stretchr/testify/require"
"google.golang.org/protobuf/reflect/protoreflect"
"google.golang.org/protobuf/types/known/anypb"
"testing"
)

func createExportedServicesResource(t *testing.T, data protoreflect.ProtoMessage) *pbresource.Resource {
res := &pbresource.Resource{
Id: &pbresource.ID{
Type: multiclusterv1alpha1.ExportedServicesType,
Name: "exported-services-1",
},
}

var err error
res.Data, err = anypb.New(data)
require.NoError(t, err)
return res
}

func validExportedServicesWithPeer() *multiclusterv1alpha1.ExportedServices {
consumers := make([]*multiclusterv1alpha1.ExportedServicesConsumer, 1)
consumers[0] = new(multiclusterv1alpha1.ExportedServicesConsumer)
consumers[0].ConsumerTenancy = &multiclusterv1alpha1.ExportedServicesConsumer_Peer{Peer: "peer"}
return &multiclusterv1alpha1.ExportedServices{
Services: []string{"api", "frontend", "backend"},
Consumers: consumers,
}
}

func validExportedServicesWithPartition() *multiclusterv1alpha1.ExportedServices {
consumers := make([]*multiclusterv1alpha1.ExportedServicesConsumer, 1)
consumers[0] = new(multiclusterv1alpha1.ExportedServicesConsumer)
consumers[0].ConsumerTenancy = &multiclusterv1alpha1.ExportedServicesConsumer_Partition{Partition: "partition"}
return &multiclusterv1alpha1.ExportedServices{
Services: []string{"api", "frontend", "backend"},
Consumers: consumers,
}
}

func validExportedServicesWithSamenessGroup() *multiclusterv1alpha1.ExportedServices {
consumers := make([]*multiclusterv1alpha1.ExportedServicesConsumer, 1)
consumers[0] = new(multiclusterv1alpha1.ExportedServicesConsumer)
consumers[0].ConsumerTenancy = &multiclusterv1alpha1.ExportedServicesConsumer_SamenessGroup{SamenessGroup: "sameness_group"}
return &multiclusterv1alpha1.ExportedServices{
Services: []string{"api", "frontend", "backend"},
Consumers: consumers,
}
}

func inValidExportedServices() *multiclusterv1alpha1.ExportedServices {
return &multiclusterv1alpha1.ExportedServices{}
}

func TestValidateExportedServicesWithPeer_Ok(t *testing.T) {
res := createExportedServicesResource(t, validExportedServicesWithPeer())

err := ValidateExportedServices(res)
require.NoError(t, err)

var resDecoded multiclusterv1alpha1.ExportedServices
err = res.Data.UnmarshalTo(&resDecoded)
require.NoError(t, err)
require.Equal(t, 1, len(resDecoded.Consumers))
require.Equal(t, "peer", resDecoded.Consumers[0].GetPeer())
}

func TestValidateExportedServicesWithPartition_Ok(t *testing.T) {
res := createExportedServicesResource(t, validExportedServicesWithPartition())

err := ValidateExportedServices(res)
require.NoError(t, err)

var resDecoded multiclusterv1alpha1.ExportedServices
err = res.Data.UnmarshalTo(&resDecoded)
require.NoError(t, err)
require.Equal(t, 1, len(resDecoded.Consumers))
require.Equal(t, "partition", resDecoded.Consumers[0].GetPartition())
}

func TestValidateExportedServicesWithSamenessGroup_Ok(t *testing.T) {
res := createExportedServicesResource(t, validExportedServicesWithSamenessGroup())

err := ValidateExportedServices(res)
require.NoError(t, err)

var resDecoded multiclusterv1alpha1.ExportedServices
err = res.Data.UnmarshalTo(&resDecoded)
require.NoError(t, err)
require.Equal(t, 1, len(resDecoded.Consumers))
require.Equal(t, "sameness_group", resDecoded.Consumers[0].GetSamenessGroup())
}

func TestValidateExportedServices_NoServices(t *testing.T) {
res := createExportedServicesResource(t, inValidExportedServices())

err := ValidateExportedServices(res)
require.Error(t, err)
expectedError := errors.New("invalid \"services\" field: at least one service must be set")
require.ErrorAs(t, err, &expectedError)
}
Loading
Loading