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鈥檒l occasionally send you account related emails.

Already on GitHub? Sign in to your account

Create anonymous-policy and token from non-default partitions. #966

Merged
merged 6 commits into from
Jan 24, 2022
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.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
2 changes: 2 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@ IMPROVEMENTS:
BUG FIXES:
* Helm
* Add `PodDisruptionBudget` Kind when checking for existing versions so that `helm template` can generate the right version. [[GH-923](https://github.com/hashicorp/consul-k8s/pull/923)]
* Control Plane
* Admin Partitions **(Consul Enterprise only)**: Attach anonymous-policy to the anonymous token from non-default partitions to support DNS queries when the default partition is on a VM. [[GH-966](https://github.com/hashicorp/consul-k8s/pull/966)]

## 0.39.0 (December 15, 2021)

Expand Down
4 changes: 2 additions & 2 deletions control-plane/connect-inject/endpoints_controller_ent_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -1180,7 +1180,7 @@ func TestReconcileUpdateEndpointWithNamespaces(t *testing.T) {
consul, err := testutil.NewTestServerConfigT(t, func(c *testutil.TestServerConfig) {
if tt.enableACLs {
c.ACL.Enabled = true
c.ACL.Tokens.Master = adminToken
c.ACL.Tokens.InitialManagement = adminToken
}
c.NodeName = nodeName
})
Expand Down Expand Up @@ -1514,7 +1514,7 @@ func TestReconcileDeleteEndpointWithNamespaces(t *testing.T) {
consul, err := testutil.NewTestServerConfigT(t, func(c *testutil.TestServerConfig) {
if tt.enableACLs {
c.ACL.Enabled = true
c.ACL.Tokens.Master = adminToken
c.ACL.Tokens.InitialManagement = adminToken
}
c.NodeName = nodeName
})
Expand Down
6 changes: 3 additions & 3 deletions control-plane/connect-inject/endpoints_controller_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -127,7 +127,7 @@ func TestProcessUpstreamsTLSandACLs(t *testing.T) {
consul, err := testutil.NewTestServerConfigT(t, func(c *testutil.TestServerConfig) {
c.ACL.Enabled = true
c.ACL.DefaultPolicy = "deny"
c.ACL.Tokens.Master = masterToken
c.ACL.Tokens.InitialManagement = masterToken
c.CAFile = caFile
c.CertFile = certFile
c.KeyFile = keyFile
Expand Down Expand Up @@ -2340,7 +2340,7 @@ func TestReconcileUpdateEndpoint(t *testing.T) {
consul, err := testutil.NewTestServerConfigT(t, func(c *testutil.TestServerConfig) {
if tt.enableACLs {
c.ACL.Enabled = tt.enableACLs
c.ACL.Tokens.Master = adminToken
c.ACL.Tokens.InitialManagement = adminToken
}
c.NodeName = nodeName
})
Expand Down Expand Up @@ -2627,7 +2627,7 @@ func TestReconcileDeleteEndpoint(t *testing.T) {
consul, err := testutil.NewTestServerConfigT(t, func(c *testutil.TestServerConfig) {
if tt.enableACLs {
c.ACL.Enabled = true
c.ACL.Tokens.Master = adminToken
c.ACL.Tokens.InitialManagement = adminToken
}
c.NodeName = nodeName
})
Expand Down
2 changes: 2 additions & 0 deletions control-plane/go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -129,4 +129,6 @@ require (
sigs.k8s.io/yaml v1.2.0 // indirect
)

replace github.com/hashicorp/consul/sdk v0.9.0 => github.com/hashicorp/consul/sdk v0.4.1-0.20220120214936-7568f3a102a8
Copy link
Contributor Author

Choose a reason for hiding this comment

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

This was to update the version of the consul/sdk without impacting the version of the consul/api.


go 1.17
4 changes: 2 additions & 2 deletions control-plane/go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -300,9 +300,9 @@ github.com/hashicorp/consul/api v1.1.0/go.mod h1:VmuI/Lkw1nC05EYQWNKwWGbkg+FbDBt
github.com/hashicorp/consul/api v1.12.0 h1:k3y1FYv6nuKyNTqj6w9gXOx5r5CfLj/k/euUeBXj1OY=
github.com/hashicorp/consul/api v1.12.0/go.mod h1:6pVBMo0ebnYdt2S3H87XhekM/HHrUoTD2XXb/VrZVy0=
github.com/hashicorp/consul/sdk v0.1.1/go.mod h1:VKf9jXwCTEY1QZP2MOLRhb5i/I/ssyNV1vwHyQBF0x8=
github.com/hashicorp/consul/sdk v0.4.1-0.20220120214936-7568f3a102a8 h1:1O/CANaJGcL6urr47PLoPZ0oQcGLUlGpYoRLYAYFSDs=
github.com/hashicorp/consul/sdk v0.4.1-0.20220120214936-7568f3a102a8/go.mod h1:GBvyrGALthsZObzUGsfgHZQDXjg4lOjagTIwIR1vPms=
github.com/hashicorp/consul/sdk v0.8.0/go.mod h1:GBvyrGALthsZObzUGsfgHZQDXjg4lOjagTIwIR1vPms=
github.com/hashicorp/consul/sdk v0.9.0 h1:NGSHAU7X3yDCjo8WBUbNOtD3BSqv8u0vu3+zNxgmxQI=
github.com/hashicorp/consul/sdk v0.9.0/go.mod h1:GBvyrGALthsZObzUGsfgHZQDXjg4lOjagTIwIR1vPms=
github.com/hashicorp/errwrap v1.0.0 h1:hLrqtEDnRye3+sgx6z4qVLNuviH3MR5aQ0ykNJa/UYA=
github.com/hashicorp/errwrap v1.0.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4=
github.com/hashicorp/go-cleanhttp v0.5.0/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80=
Expand Down
4 changes: 2 additions & 2 deletions control-plane/namespaces/namespaces_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ func TestEnsureExists_AlreadyExists(tt *testing.T) {
consul, err := testutil.NewTestServerConfigT(t, func(cfg *testutil.TestServerConfig) {
cfg.ACL.Enabled = c.ACLsEnabled
cfg.ACL.DefaultPolicy = "deny"
cfg.ACL.Tokens.Master = masterToken
cfg.ACL.Tokens.InitialManagement = masterToken
})
req.NoError(err)
defer consul.Stop()
Expand Down Expand Up @@ -104,7 +104,7 @@ func TestEnsureExists_CreatesNS(tt *testing.T) {
consul, err := testutil.NewTestServerConfigT(t, func(cfg *testutil.TestServerConfig) {
cfg.ACL.Enabled = c.ACLsEnabled
cfg.ACL.DefaultPolicy = "deny"
cfg.ACL.Tokens.Master = masterToken
cfg.ACL.Tokens.InitialManagement = masterToken
})
req.NoError(err)
defer consul.Stop()
Expand Down
2 changes: 1 addition & 1 deletion control-plane/subcommand/connect-init/command_ent_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -136,7 +136,7 @@ func TestRun_ServicePollingWithACLsAndTLSWithNamespaces(t *testing.T) {
if c.acls {
cfg.ACL.Enabled = true
cfg.ACL.DefaultPolicy = "deny"
cfg.ACL.Tokens.Master = masterToken
cfg.ACL.Tokens.InitialManagement = masterToken
}
if c.tls {
caFile, certFile, keyFile = test.GenerateServerCerts(t)
Expand Down
2 changes: 1 addition & 1 deletion control-plane/subcommand/connect-init/command_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -122,7 +122,7 @@ func TestRun_ServicePollingWithACLsAndTLS(t *testing.T) {
server, err := testutil.NewTestServerConfigT(t, func(c *testutil.TestServerConfig) {
c.ACL.Enabled = true
c.ACL.DefaultPolicy = "deny"
c.ACL.Tokens.Master = masterToken
c.ACL.Tokens.InitialManagement = masterToken
if tt.tls {
caFile, certFile, keyFile = test.GenerateServerCerts(t)
c.CAFile = caFile
Expand Down
22 changes: 15 additions & 7 deletions control-plane/subcommand/server-acl-init/command.go
Original file line number Diff line number Diff line change
Expand Up @@ -451,7 +451,21 @@ func (c *Command) Run(args []string) int {
}

if c.createAnonymousPolicy(isPrimary) {
err := c.configureAnonymousPolicy(consulClient)
// When the default partition is in a VM, the anonymous policy does not allow cross-partition
// DNS lookups. The anonymous policy in the default partition needs to be updated in order to
// support this use-case. Creating a separate anonymous token client that updates the anonymous
// policy and token in the default partition ensures this works.
anonTokenConfig := clientConfig
if c.flagEnablePartitions {
anonTokenConfig.Partition = consulDefaultPartition
}
anonTokenClient, err := consul.NewClient(anonTokenConfig)
if err != nil {
c.log.Error(err.Error())
return 1
}

err = c.configureAnonymousPolicy(anonTokenClient)
if err != nil {
c.log.Error(err.Error())
return 1
Expand Down Expand Up @@ -793,12 +807,6 @@ type Config struct {
// createAnonymousPolicy returns whether we should create a policy for the
// anonymous ACL token, i.e. queries without ACL tokens.
func (c *Command) createAnonymousPolicy(isPrimary bool) bool {
// Don't try to create the anonymous policy in non-default partitions because
// non-default partitions will use the anonymous policy from the default
// partition.
if c.flagEnablePartitions && c.flagPartitionName != "default" {
return false
}
// If isPrimary is not set then we're in a secondary DC.
// In this case we assume that the primary datacenter has already created
// the anonymous policy and attached it to the anonymous token.
Expand Down
87 changes: 87 additions & 0 deletions control-plane/subcommand/server-acl-init/command_ent_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,8 @@ import (
"strings"
"testing"

"github.com/hashicorp/consul-k8s/control-plane/consul"
"github.com/hashicorp/consul-k8s/control-plane/subcommand/common"
"github.com/hashicorp/consul/api"
"github.com/hashicorp/consul/sdk/testutil"
"github.com/mitchellh/cli"
Expand Down Expand Up @@ -206,6 +208,54 @@ func TestRun_ConnectInject_NamespaceMirroring(t *testing.T) {
}
}

// Test that the anonymous token policy is created in the default partition from
// a non-default partition.
func TestRun_AnonymousToken_CreatedFromNonDefaultPartition(t *testing.T) {
bootToken := "aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeeee"
tokenFile := common.WriteTempFile(t, bootToken)
server, stopFn := partitionedSetup(t, bootToken, "test")
defer stopFn()
k8s := fake.NewSimpleClientset()
setUpK8sServiceAccount(t, k8s, ns)

ui := cli.NewMockUi()
cmd := Command{
UI: ui,
clientset: k8s,
}
cmd.init()
args := []string{
"-server-address=" + strings.Split(server.HTTPAddr, ":")[0],
"-server-port=" + strings.Split(server.HTTPAddr, ":")[1],
"-resource-prefix=" + resourcePrefix,
"-k8s-namespace=" + ns,
"-bootstrap-token-file", tokenFile,
"-enable-partitions",
"-allow-dns",
"-partition=test",
"-enable-namespaces",
}
responseCode := cmd.Run(args)
require.Equal(t, 0, responseCode, ui.ErrorWriter.String())

consul, err := api.NewClient(&api.Config{
Address: server.HTTPAddr,
Token: bootToken,
})
require.NoError(t, err)

anonPolicyName := "anonymous-token-policy"
// Check that the anonymous token policy was created.
policy := policyExists(t, anonPolicyName, consul)
// Should be a global policy.
require.Len(t, policy.Datacenters, 0)

// Check that the anonymous token has the policy.
tokenData, _, err := consul.ACL().TokenReadSelf(&api.QueryOptions{Token: "anonymous"})
require.NoError(t, err)
require.Equal(t, anonPolicyName, tokenData.Policies[0].Name)
}

// Test that ACL policies get updated if namespaces/partition config changes.
func TestRun_ACLPolicyUpdates(t *testing.T) {
t.Parallel()
Expand Down Expand Up @@ -1037,3 +1087,40 @@ func completeEnterpriseSetup(t *testing.T) (*fake.Clientset, *testutil.TestServe

return k8s, svr
}

// partitionedSetup is a helper function which creates a server and a consul agent that runs as
// a client in the provided partitionName. The bootToken is the token used as the bootstrap token
// for both the client and the server. The helper creates a server, then creates a partition with
// the provided partitionName and then creates a client in said partition.
func partitionedSetup(t *testing.T, bootToken string, partitionName string) (*testutil.TestServer, func()) {
server, err := testutil.NewTestServerConfigT(t, func(c *testutil.TestServerConfig) {
c.ACL.Enabled = true
c.ACL.Tokens.InitialManagement = bootToken
})
require.NoError(t, err)
server.WaitForLeader(t)

serverAPIClient, err := consul.NewClient(&api.Config{
Address: server.HTTPAddr,
Token: bootToken,
})
require.NoError(t, err)

_, _, err = serverAPIClient.Partitions().Create(context.Background(), &api.Partition{Name: partitionName}, &api.WriteOptions{})
require.NoError(t, err)

partitionedClient, err := testutil.NewTestServerConfigT(t, func(c *testutil.TestServerConfig) {
c.Server = false
c.Bootstrap = false
c.Partition = partitionName
c.RetryJoin = []string{server.LANAddr}
c.ACL.Enabled = true
c.ACL.Tokens.Agent = bootToken
})
require.NoError(t, err)

return server, func() {
server.Stop()
partitionedClient.Stop()
}
}
4 changes: 2 additions & 2 deletions control-plane/subcommand/server-acl-init/command_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -2108,7 +2108,7 @@ func completeBootstrappedSetup(t *testing.T, masterToken string) (*fake.Clientse

svr, err := testutil.NewTestServerConfigT(t, func(c *testutil.TestServerConfig) {
c.ACL.Enabled = true
c.ACL.Tokens.Master = masterToken
c.ACL.Tokens.InitialManagement = masterToken
})
require.NoError(t, err)
svr.WaitForActiveCARoot(t)
Expand Down Expand Up @@ -2153,7 +2153,7 @@ func replicatedSetup(t *testing.T, bootToken string) (*fake.Clientset, *api.Clie
primarySvr, err := testutil.NewTestServerConfigT(t, func(c *testutil.TestServerConfig) {
c.ACL.Enabled = true
if bootToken != "" {
c.ACL.Tokens.Master = bootToken
c.ACL.Tokens.InitialManagement = bootToken
}
})
require.NoError(t, err)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ func TestCreateOrUpdateACLPolicy_ErrorsIfDescriptionDoesNotMatch(t *testing.T) {
bootToken := "aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeeee"
svr, err := testutil.NewTestServerConfigT(t, func(c *testutil.TestServerConfig) {
c.ACL.Enabled = true
c.ACL.Tokens.Master = bootToken
c.ACL.Tokens.InitialManagement = bootToken
})
require.NoError(err)
svr.WaitForLeader(t)
Expand Down