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

Backport of added check if anonymous token policy exists into release/1.2.x #2864

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
3 changes: 3 additions & 0 deletions .changelog/2790.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
```release-note:improvement
control-plane: prevent updation of anonymous-token-policy and anonymous-token if anonymous-token-policy is already attached to the anonymous-token
```
34 changes: 32 additions & 2 deletions control-plane/subcommand/server-acl-init/anonymous_token.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,24 @@ import (
"github.com/hashicorp/consul/api"
)

const (
anonymousTokenPolicyName = "anonymous-token-policy"
anonymousTokenAccessorID = "00000000-0000-0000-0000-000000000002"
)

// configureAnonymousPolicy sets up policies and tokens so that Consul DNS and
// cross-datacenter Consul connect calls will work.
func (c *Command) configureAnonymousPolicy(consulClient *api.Client) error {
exists, err := checkIfAnonymousTokenPolicyExists(consulClient)
if err != nil {
c.log.Error("Error checking if anonymous token policy exists", "err", err)
return err
}
if exists {
c.log.Info("skipping creating anonymous token since it already exists")
return nil
}

anonRules, err := c.anonymousTokenRules()
if err != nil {
c.log.Error("Error templating anonymous token rules", "err", err)
Expand All @@ -18,7 +33,7 @@ func (c *Command) configureAnonymousPolicy(consulClient *api.Client) error {

// Create policy for the anonymous token
anonPolicy := api.ACLPolicy{
Name: "anonymous-token-policy",
Name: anonymousTokenPolicyName,
Description: "Anonymous token Policy",
Rules: anonRules,
}
Expand All @@ -33,7 +48,7 @@ func (c *Command) configureAnonymousPolicy(consulClient *api.Client) error {

// Create token to get sent to TokenUpdate
aToken := api.ACLToken{
AccessorID: "00000000-0000-0000-0000-000000000002",
AccessorID: anonymousTokenAccessorID,
Policies: []*api.ACLTokenPolicyLink{{Name: anonPolicy.Name}},
}

Expand All @@ -44,3 +59,18 @@ func (c *Command) configureAnonymousPolicy(consulClient *api.Client) error {
return err
})
}

func checkIfAnonymousTokenPolicyExists(consulClient *api.Client) (bool, error) {
token, _, err := consulClient.ACL().TokenRead(anonymousTokenAccessorID, nil)
if err != nil {
return false, err
}

for _, policy := range token.Policies {
if policy.Name == anonymousTokenPolicyName {
return true, nil
}
}

return false, nil
}
68 changes: 68 additions & 0 deletions control-plane/subcommand/server-acl-init/anonymous_token_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
package serveraclinit

import (
"strings"
"testing"

"github.com/hashicorp/consul/api"
"github.com/mitchellh/cli"
"github.com/stretchr/testify/require"
)

func Test_configureAnonymousPolicy(t *testing.T) {

k8s, testClient := completeSetup(t)
consulHTTPAddr := testClient.TestServer.HTTPAddr
consulGRPCAddr := testClient.TestServer.GRPCAddr

setUpK8sServiceAccount(t, k8s, ns)
ui := cli.NewMockUi()
cmd := Command{
UI: ui,
clientset: k8s,
}
cmd.init()
flags := []string{"-connect-inject"}
cmdArgs := append([]string{
"-timeout=1m",
"-resource-prefix=" + resourcePrefix,
"-k8s-namespace=" + ns,
"-auth-method-host=https://my-kube.com",
"-addresses", strings.Split(consulHTTPAddr, ":")[0],
"-http-port", strings.Split(consulHTTPAddr, ":")[1],
"-grpc-port", strings.Split(consulGRPCAddr, ":")[1],
}, flags...)
responseCode := cmd.Run(cmdArgs)
require.Equal(t, 0, responseCode, ui.ErrorWriter.String())

bootToken := getBootToken(t, k8s, resourcePrefix, ns)
consul, err := api.NewClient(&api.Config{
Address: consulHTTPAddr,
Token: bootToken,
})
require.NoError(t, err)

err = cmd.configureAnonymousPolicy(consul)
require.NoError(t, err)

policy, _, err := consul.ACL().PolicyReadByName(anonymousTokenPolicyName, nil)
require.NoError(t, err)

testPolicy := api.ACLPolicy{
ID: policy.ID,
Name: anonymousTokenPolicyName,
Description: "Anonymous token Policy",
Rules: `acl = "read"`,
}
readOnlyPolicy, _, err := consul.ACL().PolicyUpdate(&testPolicy, &api.WriteOptions{})
require.NoError(t, err)

err = cmd.configureAnonymousPolicy(consul)
require.NoError(t, err)

actualPolicy, _, err := consul.ACL().PolicyReadByName(anonymousTokenPolicyName, nil)
require.NoError(t, err)

// assert policy is still same.
require.Equal(t, readOnlyPolicy, actualPolicy)
}