diff --git a/.changelog/16044.txt b/.changelog/16044.txt new file mode 100644 index 000000000..338c5c309 --- /dev/null +++ b/.changelog/16044.txt @@ -0,0 +1,3 @@ +```release-note:deprecation +cli: The `-id` flag on acl token operations has been changed to `-accessor-id` for clarity in documentation. The `-id` flag will continue to work, but operators should use `-accessor-id` in the future. +``` \ No newline at end of file diff --git a/acl/policy.go b/acl/policy.go index de97bc544..51e53be95 100644 --- a/acl/policy.go +++ b/acl/policy.go @@ -5,13 +5,6 @@ import ( "strings" ) -type SyntaxVersion int - -const ( - SyntaxCurrent SyntaxVersion = iota - SyntaxLegacy -) - const ( PolicyDeny = "deny" PolicyRead = "read" diff --git a/agent/acl_endpoint.go b/agent/acl_endpoint.go index 53a0d8519..3c5f6c7d6 100644 --- a/agent/acl_endpoint.go +++ b/agent/acl_endpoint.go @@ -295,7 +295,7 @@ func (s *HTTPHandlers) ACLTokenCRUD(resp http.ResponseWriter, req *http.Request) return nil, aclDisabled } - var fn func(resp http.ResponseWriter, req *http.Request, tokenID string) (interface{}, error) + var fn func(resp http.ResponseWriter, req *http.Request, tokenAccessorID string) (interface{}, error) switch req.Method { case "GET": @@ -311,16 +311,16 @@ func (s *HTTPHandlers) ACLTokenCRUD(resp http.ResponseWriter, req *http.Request) return nil, MethodNotAllowedError{req.Method, []string{"GET", "PUT", "DELETE"}} } - tokenID := strings.TrimPrefix(req.URL.Path, "/v1/acl/token/") - if strings.HasSuffix(tokenID, "/clone") && req.Method == "PUT" { - tokenID = tokenID[:len(tokenID)-6] + tokenAccessorID := strings.TrimPrefix(req.URL.Path, "/v1/acl/token/") + if strings.HasSuffix(tokenAccessorID, "/clone") && req.Method == "PUT" { + tokenAccessorID = tokenAccessorID[:len(tokenAccessorID)-6] fn = s.ACLTokenClone } - if tokenID == "" && req.Method != "PUT" { - return nil, HTTPError{StatusCode: http.StatusBadRequest, Reason: "Missing token ID"} + if tokenAccessorID == "" && req.Method != "PUT" { + return nil, HTTPError{StatusCode: http.StatusBadRequest, Reason: "Missing token AccessorID"} } - return fn(resp, req, tokenID) + return fn(resp, req, tokenAccessorID) } func (s *HTTPHandlers) ACLTokenSelf(resp http.ResponseWriter, req *http.Request) (interface{}, error) { @@ -336,7 +336,7 @@ func (s *HTTPHandlers) ACLTokenSelf(resp http.ResponseWriter, req *http.Request) return nil, nil } - // copy the token parameter to the ID + // copy the token secret parameter to the ID args.TokenID = args.Token if args.Datacenter == "" { @@ -364,10 +364,10 @@ func (s *HTTPHandlers) ACLTokenCreate(resp http.ResponseWriter, req *http.Reques return s.aclTokenSetInternal(req, "", true) } -func (s *HTTPHandlers) ACLTokenGet(resp http.ResponseWriter, req *http.Request, tokenID string) (interface{}, error) { +func (s *HTTPHandlers) ACLTokenGet(resp http.ResponseWriter, req *http.Request, tokenAccessorID string) (interface{}, error) { args := structs.ACLTokenGetRequest{ Datacenter: s.agent.config.Datacenter, - TokenID: tokenID, + TokenID: tokenAccessorID, TokenIDType: structs.ACLTokenAccessor, } @@ -407,11 +407,11 @@ func (s *HTTPHandlers) ACLTokenGet(resp http.ResponseWriter, req *http.Request, return out.Token, nil } -func (s *HTTPHandlers) ACLTokenSet(_ http.ResponseWriter, req *http.Request, tokenID string) (interface{}, error) { - return s.aclTokenSetInternal(req, tokenID, false) +func (s *HTTPHandlers) ACLTokenSet(_ http.ResponseWriter, req *http.Request, tokenAccessorID string) (interface{}, error) { + return s.aclTokenSetInternal(req, tokenAccessorID, false) } -func (s *HTTPHandlers) aclTokenSetInternal(req *http.Request, tokenID string, create bool) (interface{}, error) { +func (s *HTTPHandlers) aclTokenSetInternal(req *http.Request, tokenAccessorID string, create bool) (interface{}, error) { args := structs.ACLTokenSetRequest{ Datacenter: s.agent.config.Datacenter, Create: create, @@ -425,10 +425,8 @@ func (s *HTTPHandlers) aclTokenSetInternal(req *http.Request, tokenID string, cr return nil, HTTPError{StatusCode: http.StatusBadRequest, Reason: fmt.Sprintf("Token decoding failed: %v", err)} } - if !create { - if args.ACLToken.AccessorID != tokenID { - return nil, HTTPError{StatusCode: http.StatusBadRequest, Reason: "Token Accessor ID in URL and payload do not match"} - } + if !create && args.ACLToken.AccessorID != tokenAccessorID { + return nil, HTTPError{StatusCode: http.StatusBadRequest, Reason: "Token Accessor ID in URL and payload do not match"} } var out structs.ACLToken @@ -439,10 +437,10 @@ func (s *HTTPHandlers) aclTokenSetInternal(req *http.Request, tokenID string, cr return &out, nil } -func (s *HTTPHandlers) ACLTokenDelete(resp http.ResponseWriter, req *http.Request, tokenID string) (interface{}, error) { +func (s *HTTPHandlers) ACLTokenDelete(resp http.ResponseWriter, req *http.Request, tokenAccessorID string) (interface{}, error) { args := structs.ACLTokenDeleteRequest{ Datacenter: s.agent.config.Datacenter, - TokenID: tokenID, + TokenID: tokenAccessorID, } s.parseToken(req, &args.Token) if err := s.parseEntMeta(req, &args.EnterpriseMeta); err != nil { @@ -456,7 +454,7 @@ func (s *HTTPHandlers) ACLTokenDelete(resp http.ResponseWriter, req *http.Reques return true, nil } -func (s *HTTPHandlers) ACLTokenClone(resp http.ResponseWriter, req *http.Request, tokenID string) (interface{}, error) { +func (s *HTTPHandlers) ACLTokenClone(resp http.ResponseWriter, req *http.Request, tokenAccessorID string) (interface{}, error) { if s.checkACLDisabled() { return nil, aclDisabled } @@ -475,7 +473,7 @@ func (s *HTTPHandlers) ACLTokenClone(resp http.ResponseWriter, req *http.Request s.parseToken(req, &args.Token) // Set this for the ID to clone - args.ACLToken.AccessorID = tokenID + args.ACLToken.AccessorID = tokenAccessorID var out structs.ACLToken if err := s.agent.RPC(req.Context(), "ACL.TokenClone", args, &out); err != nil { diff --git a/agent/acl_test.go b/agent/acl_test.go index cc2249c67..3102da4fe 100644 --- a/agent/acl_test.go +++ b/agent/acl_test.go @@ -37,7 +37,7 @@ type TestACLAgent struct { // NewTestACLAgent does just enough so that all the code within agent/acl.go can work // Basically it needs a local state for some of the vet* functions, a logger and a delegate. -// The key is that we are the delegate so we can control the ResolveToken responses +// The key is that we are the delegate so we can control the ResolveTokenSecret responses func NewTestACLAgent(t *testing.T, name string, hcl string, resolveAuthz authzResolver, resolveIdent identResolver) *TestACLAgent { t.Helper() @@ -89,9 +89,9 @@ func NewTestACLAgent(t *testing.T, name string, hcl string, resolveAuthz authzRe return a } -func (a *TestACLAgent) ResolveToken(secretID string) (acl.Authorizer, error) { +func (a *TestACLAgent) ResolveTokenSecret(secretID string) (acl.Authorizer, error) { if a.resolveAuthzFn == nil { - return nil, fmt.Errorf("ResolveToken call is unexpected - no authz resolver callback set") + return nil, fmt.Errorf("ResolveTokenSecret call is unexpected - no authz resolver callback set") } _, authz, err := a.resolveAuthzFn(secretID) @@ -99,7 +99,7 @@ func (a *TestACLAgent) ResolveToken(secretID string) (acl.Authorizer, error) { } func (a *TestACLAgent) ResolveTokenAndDefaultMeta(secretID string, entMeta *acl.EnterpriseMeta, authzContext *acl.AuthorizerContext) (resolver.Result, error) { - authz, err := a.ResolveToken(secretID) + authz, err := a.ResolveTokenSecret(secretID) if err != nil { return resolver.Result{}, err } diff --git a/agent/agent_endpoint_test.go b/agent/agent_endpoint_test.go index d582f3eba..c9cfbee45 100644 --- a/agent/agent_endpoint_test.go +++ b/agent/agent_endpoint_test.go @@ -4418,7 +4418,7 @@ func testAgent_RegisterServiceDeregisterService_Sidecar(t *testing.T, extraHCL s } `, enableACL: true, - policies: ``, // No token rules means no valid token + policies: ``, // No policy means no valid token wantNS: nil, wantErr: "Permission denied", }, diff --git a/agent/consul/acl.go b/agent/consul/acl.go index 0c65ed9fd..a842b736e 100644 --- a/agent/consul/acl.go +++ b/agent/consul/acl.go @@ -41,7 +41,7 @@ var ACLSummaries = []prometheus.SummaryDefinition{ // These must be kept in sync with the constants in command/agent/acl.go. const ( - // anonymousToken is the token ID we re-write to if there is no token ID + // anonymousToken is the token SecretID we re-write to if there is no token ID // provided. anonymousToken = "anonymous" @@ -993,35 +993,35 @@ func (r *ACLResolver) resolveLocallyManagedToken(token string) (structs.ACLIdent return r.resolveLocallyManagedEnterpriseToken(token) } -// ResolveToken to an acl.Authorizer and structs.ACLIdentity. The acl.Authorizer -// can be used to check permissions granted to the token, and the ACLIdentity -// describes the token and any defaults applied to it. -func (r *ACLResolver) ResolveToken(token string) (resolver.Result, error) { +// ResolveTokenSecret to an acl.Authorizer and structs.ACLIdentity. The acl.Authorizer +// can be used to check permissions granted to the token using its secret, and the +// ACLIdentity describes the token and any defaults applied to it. +func (r *ACLResolver) ResolveTokenSecret(tokenSecretID string) (resolver.Result, error) { if !r.ACLsEnabled() { return resolver.Result{Authorizer: acl.ManageAll()}, nil } - if acl.RootAuthorizer(token) != nil { + if acl.RootAuthorizer(tokenSecretID) != nil { return resolver.Result{}, acl.ErrRootDenied } // handle the anonymous token - if token == "" { - token = anonymousToken + if tokenSecretID == "" { + tokenSecretID = anonymousToken } - if ident, authz, ok := r.resolveLocallyManagedToken(token); ok { + if ident, authz, ok := r.resolveLocallyManagedToken(tokenSecretID); ok { return resolver.Result{Authorizer: authz, ACLIdentity: ident}, nil } defer metrics.MeasureSince([]string{"acl", "ResolveToken"}, time.Now()) - identity, policies, err := r.resolveTokenToIdentityAndPolicies(token) + identity, policies, err := r.resolveTokenToIdentityAndPolicies(tokenSecretID) if err != nil { r.handleACLDisabledError(err) if IsACLRemoteError(err) { r.logger.Error("Error resolving token", "error", err) - ident := &missingIdentity{reason: "primary-dc-down", token: token} + ident := &missingIdentity{reason: "primary-dc-down", token: tokenSecretID} return resolver.Result{Authorizer: r.down, ACLIdentity: ident}, nil } @@ -1074,11 +1074,11 @@ func (r *ACLResolver) ACLsEnabled() bool { } func (r *ACLResolver) ResolveTokenAndDefaultMeta( - token string, + tokenSecretID string, entMeta *acl.EnterpriseMeta, authzContext *acl.AuthorizerContext, ) (resolver.Result, error) { - result, err := r.ResolveToken(token) + result, err := r.ResolveTokenSecret(tokenSecretID) if err != nil { return resolver.Result{}, err } @@ -1119,9 +1119,9 @@ func filterACLWithAuthorizer(logger hclog.Logger, authorizer acl.Authorizer, sub // filterACL uses the ACLResolver to resolve the token in an acl.Authorizer, // then uses the acl.Authorizer to filter subj. Any entities in subj that are // not authorized for read access will be removed from subj. -func filterACL(r *ACLResolver, token string, subj interface{}) error { +func filterACL(r *ACLResolver, tokenSecretID string, subj interface{}) error { // Get the ACL from the token - authorizer, err := r.ResolveToken(token) + authorizer, err := r.ResolveTokenSecret(tokenSecretID) if err != nil { return err } diff --git a/agent/consul/acl_endpoint.go b/agent/consul/acl_endpoint.go index 1cbea7779..51705b501 100644 --- a/agent/consul/acl_endpoint.go +++ b/agent/consul/acl_endpoint.go @@ -703,7 +703,7 @@ func (a *ACL) TokenBatchRead(args *structs.ACLTokenBatchGetRequest, reply *struc return err } - authz, err := a.srv.ResolveToken(args.Token) + authz, err := a.srv.ResolveTokenSecret(args.Token) if err != nil { return err } @@ -796,7 +796,7 @@ func (a *ACL) PolicyBatchRead(args *structs.ACLPolicyBatchGetRequest, reply *str return err } - authz, err := a.srv.ResolveToken(args.Token) + authz, err := a.srv.ResolveTokenSecret(args.Token) if err != nil { return err } @@ -1182,7 +1182,7 @@ func (a *ACL) RoleBatchRead(args *structs.ACLRoleBatchGetRequest, reply *structs return err } - authz, err := a.srv.ResolveToken(args.Token) + authz, err := a.srv.ResolveTokenSecret(args.Token) if err != nil { return err } @@ -2115,7 +2115,7 @@ func (a *ACL) Authorize(args *structs.RemoteACLAuthorizationRequest, reply *[]st return err } - authz, err := a.srv.ResolveToken(args.Token) + authz, err := a.srv.ResolveTokenSecret(args.Token) if err != nil { return err } diff --git a/agent/consul/acl_endpoint_test.go b/agent/consul/acl_endpoint_test.go index 618b0a427..0b5fddb6b 100644 --- a/agent/consul/acl_endpoint_test.go +++ b/agent/consul/acl_endpoint_test.go @@ -526,7 +526,7 @@ func TestACLEndpoint_TokenSet(t *testing.T) { a := ACL{srv: srv} - var tokenID string + var accessorID string t.Run("Create it", func(t *testing.T) { req := structs.ACLTokenSetRequest{ @@ -563,7 +563,7 @@ func TestACLEndpoint_TokenSet(t *testing.T) { require.Equal(t, "foo", token.NodeIdentities[0].NodeName) require.Equal(t, "dc1", token.NodeIdentities[0].Datacenter) - tokenID = token.AccessorID + accessorID = token.AccessorID }) t.Run("Update it", func(t *testing.T) { @@ -571,7 +571,7 @@ func TestACLEndpoint_TokenSet(t *testing.T) { Datacenter: "dc1", ACLToken: structs.ACLToken{ Description: "new-description", - AccessorID: tokenID, + AccessorID: accessorID, }, WriteRequest: structs.WriteRequest{Token: TestDefaultInitialManagementToken}, } @@ -1085,7 +1085,7 @@ func TestACLEndpoint_TokenSet(t *testing.T) { require.Equal(t, token.AccessorID, resp.AccessorID) requireTimeEquals(t, &expectExpTime, resp.ExpirationTime) - tokenID = token.AccessorID + accessorID = token.AccessorID }) var expTime time.Time @@ -1118,7 +1118,7 @@ func TestACLEndpoint_TokenSet(t *testing.T) { require.Equal(t, token.AccessorID, resp.AccessorID) requireTimeEquals(t, &expTime, resp.ExpirationTime) - tokenID = token.AccessorID + accessorID = token.AccessorID }) // do not insert another test at this point: these tests need to be serial @@ -1128,7 +1128,7 @@ func TestACLEndpoint_TokenSet(t *testing.T) { Datacenter: "dc1", ACLToken: structs.ACLToken{ Description: "new-description", - AccessorID: tokenID, + AccessorID: accessorID, ExpirationTime: timePointer(expTime.Add(-1 * time.Second)), }, WriteRequest: structs.WriteRequest{Token: TestDefaultInitialManagementToken}, @@ -1147,7 +1147,7 @@ func TestACLEndpoint_TokenSet(t *testing.T) { Datacenter: "dc1", ACLToken: structs.ACLToken{ Description: "new-description-1", - AccessorID: tokenID, + AccessorID: accessorID, }, WriteRequest: structs.WriteRequest{Token: TestDefaultInitialManagementToken}, } @@ -1174,7 +1174,7 @@ func TestACLEndpoint_TokenSet(t *testing.T) { Datacenter: "dc1", ACLToken: structs.ACLToken{ Description: "new-description-2", - AccessorID: tokenID, + AccessorID: accessorID, ExpirationTime: &expTime, }, WriteRequest: structs.WriteRequest{Token: TestDefaultInitialManagementToken}, diff --git a/agent/consul/acl_replication.go b/agent/consul/acl_replication.go index 5107afe45..3b41a3eec 100644 --- a/agent/consul/acl_replication.go +++ b/agent/consul/acl_replication.go @@ -313,10 +313,10 @@ func (s *Server) updateLocalACLType(ctx context.Context, logger hclog.Logger, tr return false, nil } -func (s *Server) fetchACLTokensBatch(tokenIDs []string) (*structs.ACLTokenBatchResponse, error) { +func (s *Server) fetchACLTokensBatch(tokenAccessorIDs []string) (*structs.ACLTokenBatchResponse, error) { req := structs.ACLTokenBatchGetRequest{ Datacenter: s.config.PrimaryDatacenter, - AccessorIDs: tokenIDs, + AccessorIDs: tokenAccessorIDs, QueryOptions: structs.QueryOptions{ AllowStale: true, Token: s.tokens.ReplicationToken(), diff --git a/agent/consul/acl_test.go b/agent/consul/acl_test.go index 2a5964fed..eb385d0b4 100644 --- a/agent/consul/acl_test.go +++ b/agent/consul/acl_test.go @@ -65,13 +65,13 @@ func verifyAuthorizerChain(t *testing.T, expected resolver.Result, actual resolv } func resolveTokenAsync(r *ACLResolver, token string, ch chan *asyncResolutionResult) { - authz, err := r.ResolveToken(token) + authz, err := r.ResolveTokenSecret(token) ch <- &asyncResolutionResult{authz: authz, err: err} } -func resolveToken(t *testing.T, r *ACLResolver, token string) acl.Authorizer { +func resolveTokenSecret(t *testing.T, r *ACLResolver, token string) acl.Authorizer { t.Helper() - authz, err := r.ResolveToken(token) + authz, err := r.ResolveTokenSecret(token) require.NoError(t, err) return authz } @@ -732,7 +732,7 @@ func TestACLResolver_Disabled(t *testing.T) { r := newTestACLResolver(t, delegate, nil) - authz, err := r.ResolveToken("does not exist") + authz, err := r.ResolveTokenSecret("does not exist") require.Equal(t, resolver.Result{Authorizer: acl.ManageAll()}, authz) require.Nil(t, err) } @@ -747,19 +747,19 @@ func TestACLResolver_ResolveRootACL(t *testing.T) { r := newTestACLResolver(t, delegate, nil) t.Run("Allow", func(t *testing.T) { - _, err := r.ResolveToken("allow") + _, err := r.ResolveTokenSecret("allow") require.Error(t, err) require.True(t, acl.IsErrRootDenied(err)) }) t.Run("Deny", func(t *testing.T) { - _, err := r.ResolveToken("deny") + _, err := r.ResolveTokenSecret("deny") require.Error(t, err) require.True(t, acl.IsErrRootDenied(err)) }) t.Run("Manage", func(t *testing.T) { - _, err := r.ResolveToken("manage") + _, err := r.ResolveTokenSecret("manage") require.Error(t, err) require.True(t, acl.IsErrRootDenied(err)) }) @@ -805,7 +805,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { config.Config.ACLDownPolicy = "deny" }) - authz, err := r.ResolveToken("foo") + authz, err := r.ResolveTokenSecret("foo") require.NoError(t, err) require.NotNil(t, authz) expected := resolver.Result{ @@ -833,7 +833,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { config.Config.ACLDownPolicy = "allow" }) - authz, err := r.ResolveToken("foo") + authz, err := r.ResolveTokenSecret("foo") require.NoError(t, err) require.NotNil(t, authz) expected := resolver.Result{ @@ -862,7 +862,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { config.Config.ACLRoleTTL = 0 }) - authz, err := r.ResolveToken("found") + authz, err := r.ResolveTokenSecret("found") require.NoError(t, err) require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.NodeWrite("foo", nil)) @@ -871,7 +871,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { requirePolicyCached(t, r, "dc2-key-wr", true, "cached") // from "found" token // policy cache expired - so we will fail to resolve that policy and use the default policy only - authz2, err := r.ResolveToken("found") + authz2, err := r.ResolveTokenSecret("found") require.NoError(t, err) require.NotNil(t, authz2) require.NotEqual(t, authz, authz2) @@ -899,13 +899,13 @@ func TestACLResolver_DownPolicy(t *testing.T) { config.Config.ACLRoleTTL = 0 }) - authz, err := r.ResolveToken("found-role") + authz, err := r.ResolveTokenSecret("found-role") require.NoError(t, err) require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.NodeWrite("foo", nil)) // role cache expired - so we will fail to resolve that role and use the default policy only - authz2, err := r.ResolveToken("found-role") + authz2, err := r.ResolveTokenSecret("found-role") require.NoError(t, err) require.NotNil(t, authz2) require.False(t, authz == authz2) @@ -928,14 +928,14 @@ func TestACLResolver_DownPolicy(t *testing.T) { config.Config.ACLTokenTTL = 0 }) - authz, err := r.ResolveToken("found") + authz, err := r.ResolveTokenSecret("found") require.NoError(t, err) require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.NodeWrite("foo", nil)) requireIdentityCached(t, r, "found", true, "cached") - authz2, err := r.ResolveToken("found") + authz2, err := r.ResolveTokenSecret("found") require.NoError(t, err) require.NotNil(t, authz2) verifyAuthorizerChain(t, authz, authz2) @@ -957,7 +957,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { config.Config.ACLDownPolicy = "extend-cache" }) - authz, err := r.ResolveToken("not-found") + authz, err := r.ResolveTokenSecret("not-found") require.NoError(t, err) require.NotNil(t, authz) require.Equal(t, acl.Deny, authz.NodeWrite("foo", nil)) @@ -979,14 +979,14 @@ func TestACLResolver_DownPolicy(t *testing.T) { config.Config.ACLTokenTTL = 0 }) - authz, err := r.ResolveToken("found-role") + authz, err := r.ResolveTokenSecret("found-role") require.NoError(t, err) require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.NodeWrite("foo", nil)) requireIdentityCached(t, r, "found-role", true, "still cached") - authz2, err := r.ResolveToken("found-role") + authz2, err := r.ResolveTokenSecret("found-role") require.NoError(t, err) require.NotNil(t, authz2) // testing pointer equality - these will be the same object because it is cached. @@ -1011,7 +1011,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { config.Config.ACLRoleTTL = 0 }) - authz, err := r.ResolveToken("found") + authz, err := r.ResolveTokenSecret("found") require.NoError(t, err) require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.NodeWrite("foo", nil)) @@ -1020,7 +1020,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { requirePolicyCached(t, r, "dc2-key-wr", true, "cached") // from "found" token // Will just use the policy cache - authz2, err := r.ResolveToken("found") + authz2, err := r.ResolveTokenSecret("found") require.NoError(t, err) require.NotNil(t, authz2) verifyAuthorizerChain(t, authz, authz2) @@ -1048,13 +1048,13 @@ func TestACLResolver_DownPolicy(t *testing.T) { config.Config.ACLRoleTTL = 0 }) - authz, err := r.ResolveToken("found-role") + authz, err := r.ResolveTokenSecret("found-role") require.NoError(t, err) require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.NodeWrite("foo", nil)) // Will just use the policy cache - authz2, err := r.ResolveToken("found-role") + authz2, err := r.ResolveTokenSecret("found-role") require.NoError(t, err) require.NotNil(t, authz2) verifyAuthorizerChain(t, authz, authz2) @@ -1081,7 +1081,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { config.Config.ACLRoleTTL = 0 }) - authz, err := r.ResolveToken("found") + authz, err := r.ResolveTokenSecret("found") require.NoError(t, err) require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.NodeWrite("foo", nil)) @@ -1090,7 +1090,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { requirePolicyCached(t, r, "dc2-key-wr", true, "cached") // from "found" token // The identity should have been cached so this should still be valid - authz2, err := r.ResolveToken("found") + authz2, err := r.ResolveTokenSecret("found") require.NoError(t, err) require.NotNil(t, authz2) // testing pointer equality - these will be the same object because it is cached. @@ -1099,7 +1099,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { // the go routine spawned will eventually return with a authz that doesn't have the policy retry.Run(t, func(t *retry.R) { - authz3, err := r.ResolveToken("found") + authz3, err := r.ResolveTokenSecret("found") assert.NoError(t, err) assert.NotNil(t, authz3) assert.Equal(t, acl.Deny, authz3.NodeWrite("foo", nil)) @@ -1129,13 +1129,13 @@ func TestACLResolver_DownPolicy(t *testing.T) { config.Config.ACLRoleTTL = 0 }) - authz, err := r.ResolveToken("found-role") + authz, err := r.ResolveTokenSecret("found-role") require.NoError(t, err) require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.NodeWrite("foo", nil)) // The identity should have been cached so this should still be valid - authz2, err := r.ResolveToken("found-role") + authz2, err := r.ResolveTokenSecret("found-role") require.NoError(t, err) require.NotNil(t, authz2) // testing pointer equality - these will be the same object because it is cached. @@ -1144,7 +1144,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { // the go routine spawned will eventually return with a authz that doesn't have the policy retry.Run(t, func(t *retry.R) { - authz3, err := r.ResolveToken("found-role") + authz3, err := r.ResolveTokenSecret("found-role") assert.NoError(t, err) assert.NotNil(t, authz3) assert.Equal(t, acl.Deny, authz3.NodeWrite("foo", nil)) @@ -1170,7 +1170,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { config.Config.ACLRoleTTL = 0 }) - authz, err := r.ResolveToken("found") + authz, err := r.ResolveTokenSecret("found") require.NoError(t, err) require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.NodeWrite("foo", nil)) @@ -1178,7 +1178,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { requirePolicyCached(t, r, "node-wr", true, "cached") // from "found" token requirePolicyCached(t, r, "dc2-key-wr", true, "cached") // from "found" token - authz2, err := r.ResolveToken("found") + authz2, err := r.ResolveTokenSecret("found") require.NoError(t, err) require.NotNil(t, authz2) // testing pointer equality - these will be the same object because it is cached. @@ -1206,7 +1206,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { config.Config.ACLRoleTTL = 0 }) - authz, err := r.ResolveToken("found-role") + authz, err := r.ResolveTokenSecret("found-role") require.NoError(t, err) require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.NodeWrite("foo", nil)) @@ -1214,7 +1214,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { requirePolicyCached(t, r, "node-wr", true, "still cached") // from "found" token requirePolicyCached(t, r, "dc2-key-wr", true, "still cached") // from "found" token - authz2, err := r.ResolveToken("found-role") + authz2, err := r.ResolveTokenSecret("found-role") require.NoError(t, err) require.NotNil(t, authz2) // testing pointer equality - these will be the same object because it is cached. @@ -1238,7 +1238,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { config.Config.ACLTokenTTL = 0 }) - authz, err := r.ResolveToken("found") + authz, err := r.ResolveTokenSecret("found") require.NoError(t, err) require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.NodeWrite("foo", nil)) @@ -1246,7 +1246,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { requireIdentityCached(t, r, "found", true, "cached") // The identity should have been cached so this should still be valid - authz2, err := r.ResolveToken("found") + authz2, err := r.ResolveTokenSecret("found") require.NoError(t, err) require.NotNil(t, authz2) verifyAuthorizerChain(t, authz, authz2) @@ -1254,7 +1254,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { // the go routine spawned will eventually return and this will be a not found error retry.Run(t, func(t *retry.R) { - _, err := r.ResolveToken("found") + _, err := r.ResolveTokenSecret("found") assert.Error(t, err) assert.True(t, acl.IsErrNotFound(err)) }) @@ -1305,7 +1305,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { }) // Prime the standard caches. - authz, err := r.ResolveToken(secretID) + authz, err := r.ResolveTokenSecret(secretID) require.NoError(t, err) require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.NodeWrite("foo", nil)) @@ -1319,7 +1319,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { // during token resolve. r.cache.RemovePolicy("dc2-key-wr") - _, err = r.ResolveToken(secretID) + _, err = r.ResolveTokenSecret(secretID) require.True(t, acl.IsErrNotFound(err)) requireIdentityCached(t, r, secretID, false, "identity not found cached") @@ -1365,7 +1365,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { }) // Prime the standard caches. - authz, err := r.ResolveToken(secretID) + authz, err := r.ResolveTokenSecret(secretID) require.NoError(t, err) require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.NodeWrite("foo", nil)) @@ -1379,7 +1379,7 @@ func TestACLResolver_DownPolicy(t *testing.T) { // during token resolve. r.cache.RemovePolicy("dc2-key-wr") - _, err = r.ResolveToken(secretID) + _, err = r.ResolveTokenSecret(secretID) require.True(t, acl.IsErrPermissionDenied(err)) require.Nil(t, r.cache.GetIdentityWithSecretToken(secretID), "identity not stored at all") @@ -1402,7 +1402,7 @@ func TestACLResolver_DatacenterScoping(t *testing.T) { } r := newTestACLResolver(t, delegate, nil) - authz, err := r.ResolveToken("found") + authz, err := r.ResolveTokenSecret("found") require.NotNil(t, authz) require.NoError(t, err) require.Equal(t, acl.Deny, authz.ACLRead(nil)) @@ -1424,7 +1424,7 @@ func TestACLResolver_DatacenterScoping(t *testing.T) { config.Config.Datacenter = "dc2" }) - authz, err := r.ResolveToken("found") + authz, err := r.ResolveTokenSecret("found") require.NotNil(t, authz) require.NoError(t, err) require.Equal(t, acl.Deny, authz.ACLRead(nil)) @@ -1505,7 +1505,7 @@ func TestACLResolver_Client(t *testing.T) { // Must use the token secret here in order for the cached identity // to be removed properly. Many other tests just resolve some other // random name and it wont matter but this one cannot. - authz, err := r.ResolveToken("a1a54629-5050-4d17-8a4e-560d2423f835") + authz, err := r.ResolveTokenSecret("a1a54629-5050-4d17-8a4e-560d2423f835") require.NoError(t, err) require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.NodeWrite("foo", nil)) @@ -1522,7 +1522,7 @@ func TestACLResolver_Client(t *testing.T) { // then the policy will be resolved but resolution will return ACL not found // resolution will stop with the not found error (even though we still have the // policies within the cache) - _, err = r.ResolveToken("a1a54629-5050-4d17-8a4e-560d2423f835") + _, err = r.ResolveTokenSecret("a1a54629-5050-4d17-8a4e-560d2423f835") require.EqualError(t, err, acl.ErrNotFound.Error()) require.True(t, modified) @@ -1672,7 +1672,7 @@ func testACLResolver_variousTokens(t *testing.T, delegate *ACLResolverTestDelega runTwiceAndReset("Missing Identity", func(t *testing.T) { delegate.UseTestLocalData(nil) - _, err := r.ResolveToken("doesn't exist") + _, err := r.ResolveTokenSecret("doesn't exist") require.Error(t, err) require.True(t, acl.IsErrNotFound(err)) }) @@ -1696,7 +1696,7 @@ func testACLResolver_variousTokens(t *testing.T, delegate *ACLResolverTestDelega RaftIndex: structs.RaftIndex{CreateIndex: 1, ModifyIndex: 2}, }, }) - authz := resolveToken(t, r, "missing-policy") + authz := resolveTokenSecret(t, r, "missing-policy") require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.ACLRead(nil)) require.Equal(t, acl.Deny, authz.NodeWrite("foo", nil)) @@ -1729,7 +1729,7 @@ func testACLResolver_variousTokens(t *testing.T, delegate *ACLResolverTestDelega RaftIndex: structs.RaftIndex{CreateIndex: 1, ModifyIndex: 2}, }, }) - authz := resolveToken(t, r, "missing-role") + authz := resolveTokenSecret(t, r, "missing-role") require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.ACLRead(nil)) require.Equal(t, acl.Deny, authz.NodeWrite("foo", nil)) @@ -1763,7 +1763,7 @@ func testACLResolver_variousTokens(t *testing.T, delegate *ACLResolverTestDelega RaftIndex: structs.RaftIndex{CreateIndex: 1, ModifyIndex: 2}, }, }) - authz := resolveToken(t, r, "missing-policy-on-role") + authz := resolveTokenSecret(t, r, "missing-policy-on-role") require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.ACLRead(nil)) require.Equal(t, acl.Deny, authz.NodeWrite("foo", nil)) @@ -1796,7 +1796,7 @@ func testACLResolver_variousTokens(t *testing.T, delegate *ACLResolverTestDelega RaftIndex: structs.RaftIndex{CreateIndex: 1, ModifyIndex: 2}, }, }) - authz := resolveToken(t, r, "found") + authz := resolveTokenSecret(t, r, "found") require.NotNil(t, authz) require.Equal(t, acl.Deny, authz.ACLRead(nil)) require.Equal(t, acl.Allow, authz.NodeWrite("foo", nil)) @@ -1837,7 +1837,7 @@ func testACLResolver_variousTokens(t *testing.T, delegate *ACLResolverTestDelega RaftIndex: structs.RaftIndex{CreateIndex: 1, ModifyIndex: 2}, }, }) - authz := resolveToken(t, r, "found-role") + authz := resolveTokenSecret(t, r, "found-role") require.NotNil(t, authz) require.Equal(t, acl.Deny, authz.ACLRead(nil)) require.Equal(t, acl.Allow, authz.NodeWrite("foo", nil)) @@ -1889,7 +1889,7 @@ func testACLResolver_variousTokens(t *testing.T, delegate *ACLResolverTestDelega RaftIndex: structs.RaftIndex{CreateIndex: 1, ModifyIndex: 2}, }, }) - authz := resolveToken(t, r, "found-policy-and-role") + authz := resolveTokenSecret(t, r, "found-policy-and-role") require.NotNil(t, authz) require.Equal(t, acl.Deny, authz.ACLRead(nil)) require.Equal(t, acl.Allow, authz.NodeWrite("foo", nil)) @@ -1921,7 +1921,7 @@ func testACLResolver_variousTokens(t *testing.T, delegate *ACLResolverTestDelega }, }, }) - authz := resolveToken(t, r, "found-role-node-identity") + authz := resolveTokenSecret(t, r, "found-role-node-identity") require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.NodeWrite("test-node", nil)) require.Equal(t, acl.Deny, authz.NodeWrite("test-node-dc2", nil)) @@ -1981,7 +1981,7 @@ func testACLResolver_variousTokens(t *testing.T, delegate *ACLResolverTestDelega // to verify that the keys for caching synthetic policies don't bleed // over between each other. t.Run("synthetic-policy-1", func(t *testing.T) { // service identity - authz, err := r.ResolveToken("found-synthetic-policy-1") + authz, err := r.ResolveTokenSecret("found-synthetic-policy-1") require.NotNil(t, authz) require.NoError(t, err) // spot check some random perms @@ -1995,7 +1995,7 @@ func testACLResolver_variousTokens(t *testing.T, delegate *ACLResolverTestDelega require.Equal(t, acl.Allow, authz.NodeRead("any-node", nil)) }) t.Run("synthetic-policy-2", func(t *testing.T) { // service identity - authz, err := r.ResolveToken("found-synthetic-policy-2") + authz, err := r.ResolveTokenSecret("found-synthetic-policy-2") require.NotNil(t, authz) require.NoError(t, err) // spot check some random perms @@ -2009,7 +2009,7 @@ func testACLResolver_variousTokens(t *testing.T, delegate *ACLResolverTestDelega require.Equal(t, acl.Allow, authz.NodeRead("any-node", nil)) }) t.Run("synthetic-policy-3", func(t *testing.T) { // node identity - authz, err := r.ResolveToken("found-synthetic-policy-3") + authz, err := r.ResolveTokenSecret("found-synthetic-policy-3") require.NoError(t, err) require.NotNil(t, authz) @@ -2025,7 +2025,7 @@ func testACLResolver_variousTokens(t *testing.T, delegate *ACLResolverTestDelega require.Equal(t, acl.Deny, authz.NodeWrite("test-node-dc2", nil)) }) t.Run("synthetic-policy-4", func(t *testing.T) { // node identity - authz, err := r.ResolveToken("found-synthetic-policy-4") + authz, err := r.ResolveTokenSecret("found-synthetic-policy-4") require.NoError(t, err) require.NotNil(t, authz) @@ -2060,7 +2060,7 @@ func testACLResolver_variousTokens(t *testing.T, delegate *ACLResolverTestDelega RaftIndex: structs.RaftIndex{CreateIndex: 1, ModifyIndex: 2}, }, }) - authz, err := r.ResolveToken("") + authz, err := r.ResolveTokenSecret("") require.NotNil(t, authz) require.NoError(t, err) require.Equal(t, acl.Deny, authz.ACLRead(nil)) @@ -2084,7 +2084,7 @@ func testACLResolver_variousTokens(t *testing.T, delegate *ACLResolverTestDelega RaftIndex: structs.RaftIndex{CreateIndex: 1, ModifyIndex: 2}, }, }) - authz, err := r.ResolveToken("with-intentions") + authz, err := r.ResolveTokenSecret("with-intentions") require.NoError(t, err) require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.ServiceRead("", nil)) @@ -2165,7 +2165,7 @@ func TestACLResolver_AgentRecovery(t *testing.T) { tokens.UpdateAgentRecoveryToken("9a184a11-5599-459e-b71a-550e5f9a5a23", token.TokenSourceConfig) - authz, err := r.ResolveToken("9a184a11-5599-459e-b71a-550e5f9a5a23") + authz, err := r.ResolveTokenSecret("9a184a11-5599-459e-b71a-550e5f9a5a23") require.NoError(t, err) require.NotNil(t, authz.ACLIdentity) require.Equal(t, "agent-recovery:foo", authz.ACLIdentity.ID()) @@ -2189,7 +2189,7 @@ func TestACLResolver_ServerManagementToken(t *testing.T) { cfg.Config.NodeName = "foo" }) - authz, err := r.ResolveToken(testToken) + authz, err := r.ResolveTokenSecret(testToken) require.NoError(t, err) require.NotNil(t, authz.ACLIdentity) require.Equal(t, structs.ServerManagementTokenAccessorID, authz.ACLIdentity.ID()) @@ -2292,7 +2292,7 @@ func TestACLResolver_ResolveToken_UpdatesPurgeTheCache(t *testing.T) { require.NoError(t, err) testutil.RunStep(t, "first resolve", func(t *testing.T) { - authz, err := srv.ACLResolver.ResolveToken(token) + authz, err := srv.ACLResolver.ResolveTokenSecret(token) require.NoError(t, err) require.NotNil(t, authz) require.Equal(t, acl.Allow, authz.KeyRead("foo", nil)) @@ -2311,7 +2311,7 @@ func TestACLResolver_ResolveToken_UpdatesPurgeTheCache(t *testing.T) { err := msgpackrpc.CallWithCodec(codec, "ACL.PolicySet", &reqPolicy, &structs.ACLPolicy{}) require.NoError(t, err) - authz, err := srv.ACLResolver.ResolveToken(token) + authz, err := srv.ACLResolver.ResolveTokenSecret(token) require.NoError(t, err) require.NotNil(t, authz) require.Equal(t, acl.Deny, authz.KeyRead("foo", nil)) @@ -2327,7 +2327,7 @@ func TestACLResolver_ResolveToken_UpdatesPurgeTheCache(t *testing.T) { err := msgpackrpc.CallWithCodec(codec, "ACL.TokenDelete", &req, &resp) require.NoError(t, err) - _, err = srv.ACLResolver.ResolveToken(token) + _, err = srv.ACLResolver.ResolveTokenSecret(token) require.True(t, acl.IsErrNotFound(err), "Error %v is not acl.ErrNotFound", err) }) } diff --git a/agent/consul/connect_ca_endpoint.go b/agent/consul/connect_ca_endpoint.go index 29cfc38be..dfd7ee4ed 100644 --- a/agent/consul/connect_ca_endpoint.go +++ b/agent/consul/connect_ca_endpoint.go @@ -60,7 +60,7 @@ func (s *ConnectCA) ConfigurationGet( } // This action requires operator read access. - authz, err := s.srv.ResolveToken(args.Token) + authz, err := s.srv.ResolveTokenSecret(args.Token) if err != nil { return err } @@ -92,7 +92,7 @@ func (s *ConnectCA) ConfigurationSet( } // This action requires operator write access. - authz, err := s.srv.ResolveToken(args.Token) + authz, err := s.srv.ResolveTokenSecret(args.Token) if err != nil { return err } @@ -149,7 +149,7 @@ func (s *ConnectCA) Sign( return err } - authz, err := s.srv.ResolveToken(args.Token) + authz, err := s.srv.ResolveTokenSecret(args.Token) if err != nil { return err } @@ -181,7 +181,7 @@ func (s *ConnectCA) SignIntermediate( } // This action requires operator write access. - authz, err := s.srv.ResolveToken(args.Token) + authz, err := s.srv.ResolveTokenSecret(args.Token) if err != nil { return err } diff --git a/agent/consul/federation_state_endpoint.go b/agent/consul/federation_state_endpoint.go index 6aade9488..69004425a 100644 --- a/agent/consul/federation_state_endpoint.go +++ b/agent/consul/federation_state_endpoint.go @@ -58,7 +58,7 @@ func (c *FederationState) Apply(args *structs.FederationStateRequest, reply *boo defer metrics.MeasureSince([]string{"federation_state", "apply"}, time.Now()) // Fetch the ACL token, if any. - authz, err := c.srv.ResolveToken(args.Token) + authz, err := c.srv.ResolveTokenSecret(args.Token) if err != nil { return err } @@ -104,7 +104,7 @@ func (c *FederationState) Get(args *structs.FederationStateQuery, reply *structs defer metrics.MeasureSince([]string{"federation_state", "get"}, time.Now()) // Fetch the ACL token, if any. - authz, err := c.srv.ResolveToken(args.Token) + authz, err := c.srv.ResolveTokenSecret(args.Token) if err != nil { return err } @@ -143,7 +143,7 @@ func (c *FederationState) List(args *structs.DCSpecificRequest, reply *structs.I defer metrics.MeasureSince([]string{"federation_state", "list"}, time.Now()) // Fetch the ACL token, if any. - authz, err := c.srv.ResolveToken(args.Token) + authz, err := c.srv.ResolveTokenSecret(args.Token) if err != nil { return err } diff --git a/agent/consul/internal_endpoint.go b/agent/consul/internal_endpoint.go index 2b5e8a194..8b5c4a5eb 100644 --- a/agent/consul/internal_endpoint.go +++ b/agent/consul/internal_endpoint.go @@ -780,7 +780,7 @@ func (m *Internal) KeyringOperation( } // Check ACLs - authz, err := m.srv.ACLResolver.ResolveToken(args.Token) + authz, err := m.srv.ACLResolver.ResolveTokenSecret(args.Token) if err != nil { return err } diff --git a/agent/consul/operator_autopilot_endpoint.go b/agent/consul/operator_autopilot_endpoint.go index babbb7956..eefecd92e 100644 --- a/agent/consul/operator_autopilot_endpoint.go +++ b/agent/consul/operator_autopilot_endpoint.go @@ -16,7 +16,7 @@ func (op *Operator) AutopilotGetConfiguration(args *structs.DCSpecificRequest, r } // This action requires operator read access. - authz, err := op.srv.ACLResolver.ResolveToken(args.Token) + authz, err := op.srv.ACLResolver.ResolveTokenSecret(args.Token) if err != nil { return err } @@ -49,7 +49,7 @@ func (op *Operator) AutopilotSetConfiguration(args *structs.AutopilotSetConfigRe } // This action requires operator write access. - authz, err := op.srv.ACLResolver.ResolveToken(args.Token) + authz, err := op.srv.ACLResolver.ResolveTokenSecret(args.Token) if err != nil { return err } @@ -81,7 +81,7 @@ func (op *Operator) ServerHealth(args *structs.DCSpecificRequest, reply *structs } // This action requires operator read access. - authz, err := op.srv.ACLResolver.ResolveToken(args.Token) + authz, err := op.srv.ACLResolver.ResolveTokenSecret(args.Token) if err != nil { return err } @@ -145,7 +145,7 @@ func (op *Operator) AutopilotState(args *structs.DCSpecificRequest, reply *autop } // This action requires operator read access. - authz, err := op.srv.ACLResolver.ResolveToken(args.Token) + authz, err := op.srv.ACLResolver.ResolveTokenSecret(args.Token) if err != nil { return err } diff --git a/agent/consul/operator_raft_endpoint.go b/agent/consul/operator_raft_endpoint.go index a0c194e7a..35f657afa 100644 --- a/agent/consul/operator_raft_endpoint.go +++ b/agent/consul/operator_raft_endpoint.go @@ -2,7 +2,6 @@ package consul import ( "fmt" - "net" "github.com/hashicorp/raft" @@ -19,7 +18,7 @@ func (op *Operator) RaftGetConfiguration(args *structs.DCSpecificRequest, reply } // This action requires operator read access. - authz, err := op.srv.ResolveToken(args.Token) + authz, err := op.srv.ResolveTokenSecret(args.Token) if err != nil { return err } @@ -81,7 +80,7 @@ func (op *Operator) RaftRemovePeerByAddress(args *structs.RaftRemovePeerRequest, // This is a super dangerous operation that requires operator write // access. - authz, err := op.srv.ACLResolver.ResolveToken(args.Token) + authz, err := op.srv.ACLResolver.ResolveTokenSecret(args.Token) if err != nil { return err } @@ -134,7 +133,7 @@ func (op *Operator) RaftRemovePeerByID(args *structs.RaftRemovePeerRequest, repl // This is a super dangerous operation that requires operator write // access. - authz, err := op.srv.ACLResolver.ResolveToken(args.Token) + authz, err := op.srv.ACLResolver.ResolveTokenSecret(args.Token) if err != nil { return err } diff --git a/agent/consul/prepared_query_endpoint.go b/agent/consul/prepared_query_endpoint.go index ffa4b5e50..fbda7924b 100644 --- a/agent/consul/prepared_query_endpoint.go +++ b/agent/consul/prepared_query_endpoint.go @@ -78,7 +78,7 @@ func (p *PreparedQuery) Apply(args *structs.PreparedQueryRequest, reply *string) *reply = args.Query.ID // Get the ACL token for the request for the checks below. - authz, err := p.srv.ResolveToken(args.Token) + authz, err := p.srv.ResolveTokenSecret(args.Token) if err != nil { return err } diff --git a/agent/consul/snapshot_endpoint.go b/agent/consul/snapshot_endpoint.go index 102bc0a38..bdbd3426b 100644 --- a/agent/consul/snapshot_endpoint.go +++ b/agent/consul/snapshot_endpoint.go @@ -58,7 +58,7 @@ func (s *Server) dispatchSnapshotRequest(args *structs.SnapshotRequest, in io.Re // Verify token is allowed to operate on snapshots. There's only a // single ACL sense here (not read and write) since reading gets you // all the ACLs and you could escalate from there. - if authz, err := s.ResolveToken(args.Token); err != nil { + if authz, err := s.ResolveTokenSecret(args.Token); err != nil { return nil, err } else if err := authz.ToAllowAuthorizer().SnapshotAllowed(nil); err != nil { return nil, err diff --git a/agent/consul/state/acl.go b/agent/consul/state/acl.go index a1308f8fe..1b7debe36 100644 --- a/agent/consul/state/acl.go +++ b/agent/consul/state/acl.go @@ -765,8 +765,8 @@ func (s *Store) ACLTokenBatchDelete(idx uint64, tokenIDs []string) error { tx := s.db.WriteTxn(idx) defer tx.Abort() - for _, tokenID := range tokenIDs { - if err := aclTokenDeleteTxn(tx, idx, tokenID, indexAccessor, nil); err != nil { + for _, accessorID := range tokenIDs { + if err := aclTokenDeleteTxn(tx, idx, accessorID, indexAccessor, nil); err != nil { return err } } diff --git a/agent/consul/txn_endpoint.go b/agent/consul/txn_endpoint.go index a1977b919..855c461fc 100644 --- a/agent/consul/txn_endpoint.go +++ b/agent/consul/txn_endpoint.go @@ -147,7 +147,7 @@ func (t *Txn) Apply(args *structs.TxnRequest, reply *structs.TxnResponse) error defer metrics.MeasureSince([]string{"txn", "apply"}, time.Now()) // Run the pre-checks before we send the transaction into Raft. - authz, err := t.srv.ResolveToken(args.Token) + authz, err := t.srv.ResolveTokenSecret(args.Token) if err != nil { return err } @@ -191,7 +191,7 @@ func (t *Txn) Read(args *structs.TxnReadRequest, reply *structs.TxnReadResponse) } // Run the pre-checks before we perform the read. - authz, err := t.srv.ResolveToken(args.Token) + authz, err := t.srv.ResolveTokenSecret(args.Token) if err != nil { return err } diff --git a/agent/structs/acl.go b/agent/structs/acl.go index fa89986a3..13424811a 100644 --- a/agent/structs/acl.go +++ b/agent/structs/acl.go @@ -1244,7 +1244,7 @@ func (r *ACLTokenSetRequest) RequestDatacenter() string { // ACLTokenGetRequest is used for token read operations at the RPC layer type ACLTokenGetRequest struct { - TokenID string // id used for the token lookup + TokenID string // Accessor ID used for the token lookup TokenIDType ACLTokenIDType // The Type of ID used to lookup the token Expanded bool Datacenter string // The datacenter to perform the request within @@ -1258,7 +1258,7 @@ func (r *ACLTokenGetRequest) RequestDatacenter() string { // ACLTokenDeleteRequest is used for token deletion operations at the RPC layer type ACLTokenDeleteRequest struct { - TokenID string // ID of the token to delete + TokenID string // Accessor ID of the token to delete Datacenter string // The datacenter to perform the request within acl.EnterpriseMeta WriteRequest diff --git a/agent/xds/server.go b/agent/xds/server.go index ba1e911db..32177b83d 100644 --- a/agent/xds/server.go +++ b/agent/xds/server.go @@ -7,6 +7,7 @@ import ( "time" envoy_discovery_v3 "github.com/envoyproxy/go-control-plane/envoy/service/discovery/v3" + "github.com/hashicorp/consul/envoyextensions/xdscommon" "github.com/armon/go-metrics" @@ -102,11 +103,11 @@ type ProxyConfigSource interface { // A full description of the XDS protocol can be found at // https://www.envoyproxy.io/docs/envoy/latest/api-docs/xds_protocol type Server struct { - NodeName string - Logger hclog.Logger - CfgSrc ProxyConfigSource - ResolveToken ACLResolverFunc - CfgFetcher ConfigFetcher + NodeName string + Logger hclog.Logger + CfgSrc ProxyConfigSource + ResolveTokenSecret ACLResolverFunc + CfgFetcher ConfigFetcher // AuthCheckFrequency is how often we should re-check the credentials used // during a long-lived gRPC Stream after it has been initially established. @@ -156,14 +157,14 @@ func NewServer( nodeName string, logger hclog.Logger, cfgMgr ProxyConfigSource, - resolveToken ACLResolverFunc, + resolveTokenSecret ACLResolverFunc, cfgFetcher ConfigFetcher, ) *Server { return &Server{ NodeName: nodeName, Logger: logger, CfgSrc: cfgMgr, - ResolveToken: resolveToken, + ResolveTokenSecret: resolveTokenSecret, CfgFetcher: cfgFetcher, AuthCheckFrequency: DefaultAuthCheckFrequency, activeStreams: &activeStreamCounters{}, @@ -190,7 +191,7 @@ func (s *Server) authenticate(ctx context.Context) (acl.Authorizer, error) { return nil, status.Errorf(codes.Internal, "error fetching options from context: %v", err) } - authz, err := s.ResolveToken(options.Token) + authz, err := s.ResolveTokenSecret(options.Token) if acl.IsErrNotFound(err) { return nil, status.Errorf(codes.Unauthenticated, "unauthenticated: %v", err) } else if acl.IsErrPermissionDenied(err) { diff --git a/agent/xds/xds_protocol_helpers_test.go b/agent/xds/xds_protocol_helpers_test.go index 6b0fe4ed2..8c4481515 100644 --- a/agent/xds/xds_protocol_helpers_test.go +++ b/agent/xds/xds_protocol_helpers_test.go @@ -159,7 +159,7 @@ type testServerScenario struct { func newTestServerDeltaScenario( t *testing.T, - resolveToken ACLResolverFunc, + resolveTokenSecret ACLResolverFunc, proxyID string, token string, authCheckFrequency time.Duration, @@ -185,7 +185,7 @@ func newTestServerDeltaScenario( "node-123", testutil.Logger(t), mgr, - resolveToken, + resolveTokenSecret, nil, /*cfgFetcher ConfigFetcher*/ ) if authCheckFrequency > 0 { diff --git a/api/acl.go b/api/acl.go index 89a6a5618..3e13ccc88 100644 --- a/api/acl.go +++ b/api/acl.go @@ -746,14 +746,14 @@ func (a *ACL) TokenUpdate(token *ACLToken, q *WriteOptions) (*ACLToken, *WriteMe // TokenClone will create a new token with the same policies and locality as the original // token but will have its own auto-generated AccessorID and SecretID as well having the -// description passed to this function. The tokenID parameter must be a valid Accessor ID +// description passed to this function. The accessorID parameter must be a valid Accessor ID // of an existing token. -func (a *ACL) TokenClone(tokenID string, description string, q *WriteOptions) (*ACLToken, *WriteMeta, error) { - if tokenID == "" { - return nil, nil, fmt.Errorf("Must specify a tokenID for Token Cloning") +func (a *ACL) TokenClone(accessorID string, description string, q *WriteOptions) (*ACLToken, *WriteMeta, error) { + if accessorID == "" { + return nil, nil, fmt.Errorf("Must specify a token AccessorID for Token Cloning") } - r := a.c.newRequest("PUT", "/v1/acl/token/"+tokenID+"/clone") + r := a.c.newRequest("PUT", "/v1/acl/token/"+accessorID+"/clone") r.setWriteOptions(q) r.obj = struct{ Description string }{description} rtt, resp, err := a.c.doRequest(r) @@ -773,10 +773,10 @@ func (a *ACL) TokenClone(tokenID string, description string, q *WriteOptions) (* return &out, wm, nil } -// TokenDelete removes a single ACL token. The tokenID parameter must be a valid +// TokenDelete removes a single ACL token. The accessorID parameter must be a valid // Accessor ID of an existing token. -func (a *ACL) TokenDelete(tokenID string, q *WriteOptions) (*WriteMeta, error) { - r := a.c.newRequest("DELETE", "/v1/acl/token/"+tokenID) +func (a *ACL) TokenDelete(accessorID string, q *WriteOptions) (*WriteMeta, error) { + r := a.c.newRequest("DELETE", "/v1/acl/token/"+accessorID) r.setWriteOptions(q) rtt, resp, err := a.c.doRequest(r) if err != nil { @@ -791,10 +791,10 @@ func (a *ACL) TokenDelete(tokenID string, q *WriteOptions) (*WriteMeta, error) { return wm, nil } -// TokenRead retrieves the full token details. The tokenID parameter must be a valid +// TokenRead retrieves the full token details. The accessorID parameter must be a valid // Accessor ID of an existing token. -func (a *ACL) TokenRead(tokenID string, q *QueryOptions) (*ACLToken, *QueryMeta, error) { - r := a.c.newRequest("GET", "/v1/acl/token/"+tokenID) +func (a *ACL) TokenRead(accessorID string, q *QueryOptions) (*ACLToken, *QueryMeta, error) { + r := a.c.newRequest("GET", "/v1/acl/token/"+accessorID) r.setQueryOptions(q) rtt, resp, err := a.c.doRequest(r) if err != nil { @@ -817,9 +817,9 @@ func (a *ACL) TokenRead(tokenID string, q *QueryOptions) (*ACLToken, *QueryMeta, } // TokenReadExpanded retrieves the full token details, as well as the contents of any policies affecting the token. -// The tokenID parameter must be a valid Accessor ID of an existing token. -func (a *ACL) TokenReadExpanded(tokenID string, q *QueryOptions) (*ACLTokenExpanded, *QueryMeta, error) { - r := a.c.newRequest("GET", "/v1/acl/token/"+tokenID) +// The accessorID parameter must be a valid Accessor ID of an existing token. +func (a *ACL) TokenReadExpanded(accessorID string, q *QueryOptions) (*ACLTokenExpanded, *QueryMeta, error) { + r := a.c.newRequest("GET", "/v1/acl/token/"+accessorID) r.setQueryOptions(q) r.params.Set("expanded", "true") rtt, resp, err := a.c.doRequest(r) diff --git a/command/acl/acl_helpers.go b/command/acl/acl_helpers.go index ea51fad80..39c6f975e 100644 --- a/command/acl/acl_helpers.go +++ b/command/acl/acl_helpers.go @@ -9,14 +9,14 @@ import ( "github.com/hashicorp/consul/api" ) -func GetTokenIDFromPartial(client *api.Client, partialID string) (string, error) { - if partialID == "anonymous" { +func GetTokenAccessorIDFromPartial(client *api.Client, partialAccessorID string) (string, error) { + if partialAccessorID == "anonymous" { return acl.AnonymousTokenID, nil } // the full UUID string was given - if len(partialID) == 36 { - return partialID, nil + if len(partialAccessorID) == 36 { + return partialAccessorID, nil } tokens, _, err := client.ACL().TokenList(nil) @@ -24,21 +24,21 @@ func GetTokenIDFromPartial(client *api.Client, partialID string) (string, error) return "", err } - tokenID := "" + tokenAccessorID := "" for _, token := range tokens { - if strings.HasPrefix(token.AccessorID, partialID) { - if tokenID != "" { + if strings.HasPrefix(token.AccessorID, partialAccessorID) { + if tokenAccessorID != "" { return "", fmt.Errorf("Partial token ID is not unique") } - tokenID = token.AccessorID + tokenAccessorID = token.AccessorID } } - if tokenID == "" { - return "", fmt.Errorf("No such token ID with prefix: %s", partialID) + if tokenAccessorID == "" { + return "", fmt.Errorf("No such token ID with prefix: %s", partialAccessorID) } - return tokenID, nil + return tokenAccessorID, nil } func GetPolicyIDFromPartial(client *api.Client, partialID string) (string, error) { diff --git a/command/acl/token/clone/token_clone.go b/command/acl/token/clone/token_clone.go index c7c90435f..aae26ff37 100644 --- a/command/acl/token/clone/token_clone.go +++ b/command/acl/token/clone/token_clone.go @@ -24,14 +24,16 @@ type cmd struct { http *flags.HTTPFlags help string - tokenID string - description string - format string + tokenAccessorID string + description string + format string + + tokenID string // DEPRECATED } func (c *cmd) init() { c.flags = flag.NewFlagSet("", flag.ContinueOnError) - c.flags.StringVar(&c.tokenID, "id", "", "The Accessor ID of the token to clone. "+ + c.flags.StringVar(&c.tokenAccessorID, "accessor-id", "", "The Accessor ID of the token to clone. "+ "It may be specified as a unique ID prefix but will error if the prefix "+ "matches multiple token Accessor IDs. The special value of 'anonymous' may "+ "be provided instead of the anonymous tokens accessor ID") @@ -47,6 +49,10 @@ func (c *cmd) init() { flags.Merge(c.flags, c.http.ServerFlags()) flags.Merge(c.flags, c.http.MultiTenancyFlags()) c.help = flags.Usage(help, c.flags) + + // Deprecations + c.flags.StringVar(&c.tokenID, "id", "", + "DEPRECATED. Use -accessor-id instead.") } func (c *cmd) Run(args []string) int { @@ -54,9 +60,15 @@ func (c *cmd) Run(args []string) int { return 1 } - if c.tokenID == "" { - c.UI.Error(fmt.Sprintf("Cannot update a token without specifying the -id parameter")) - return 1 + tokenAccessor := c.tokenAccessorID + if tokenAccessor == "" { + if c.tokenID == "" { + c.UI.Error("Cannot update a token without specifying the -accessor-id parameter") + return 1 + } else { + tokenAccessor = c.tokenID + c.UI.Warn("The -id parameter is deprecated. Use the -accessor-id parameter instead.") + } } client, err := c.http.APIClient() @@ -65,13 +77,13 @@ func (c *cmd) Run(args []string) int { return 1 } - tokenID, err := acl.GetTokenIDFromPartial(client, c.tokenID) + tok, err := acl.GetTokenAccessorIDFromPartial(client, tokenAccessor) if err != nil { - c.UI.Error(fmt.Sprintf("Error determining token ID: %v", err)) + c.UI.Error(fmt.Sprintf("Error determining token Accessor ID: %v", err)) return 1 } - t, _, err := client.ACL().TokenClone(tokenID, c.description, nil) + t, _, err := client.ACL().TokenClone(tok, c.description, nil) if err != nil { c.UI.Error(fmt.Sprintf("Error cloning token: %v", err)) return 1 @@ -112,6 +124,6 @@ Usage: consul acl token clone [options] Example: - $ consul acl token clone -id abcd -description "replication" + $ consul acl token clone -accessor-id abcd -description "replication" ` ) diff --git a/command/acl/token/clone/token_clone_test.go b/command/acl/token/clone/token_clone_test.go index 88a393ecf..8f0294222 100644 --- a/command/acl/token/clone/token_clone_test.go +++ b/command/acl/token/clone/token_clone_test.go @@ -100,7 +100,7 @@ func TestTokenCloneCommand_Pretty(t *testing.T) { args := []string{ "-http-addr=" + a.HTTPAddr(), - "-id=" + token.AccessorID, + "-accessor-id=" + token.AccessorID, "-token=root", "-description=test cloned", } @@ -136,7 +136,7 @@ func TestTokenCloneCommand_Pretty(t *testing.T) { args := []string{ "-http-addr=" + a.HTTPAddr(), - "-id=" + token.AccessorID, + "-accessor-id=" + token.AccessorID, "-token=root", } @@ -207,7 +207,7 @@ func TestTokenCloneCommand_JSON(t *testing.T) { args := []string{ "-http-addr=" + a.HTTPAddr(), - "-id=" + token.AccessorID, + "-accessor-id=" + token.AccessorID, "-token=root", "-description=test cloned", "-format=json", @@ -230,7 +230,7 @@ func TestTokenCloneCommand_JSON(t *testing.T) { args := []string{ "-http-addr=" + a.HTTPAddr(), - "-id=" + token.AccessorID, + "-accessor-id=" + token.AccessorID, "-token=root", "-format=json", } diff --git a/command/acl/token/delete/token_delete.go b/command/acl/token/delete/token_delete.go index 4d265bcf6..80ad4b6c2 100644 --- a/command/acl/token/delete/token_delete.go +++ b/command/acl/token/delete/token_delete.go @@ -17,17 +17,18 @@ func New(ui cli.Ui) *cmd { } type cmd struct { - UI cli.Ui - flags *flag.FlagSet - http *flags.HTTPFlags - help string + UI cli.Ui + flags *flag.FlagSet + http *flags.HTTPFlags + help string + tokenAccessorID string - tokenID string + tokenID string // DEPRECATED } func (c *cmd) init() { c.flags = flag.NewFlagSet("", flag.ContinueOnError) - c.flags.StringVar(&c.tokenID, "id", "", "The Accessor ID of the token to delete. "+ + c.flags.StringVar(&c.tokenAccessorID, "accessor-id", "", "The Accessor ID of the token to delete. "+ "It may be specified as a unique ID prefix but will error if the prefix "+ "matches multiple token Accessor IDs") c.http = &flags.HTTPFlags{} @@ -36,6 +37,10 @@ func (c *cmd) init() { flags.Merge(c.flags, c.http.ServerFlags()) flags.Merge(c.flags, c.http.MultiTenancyFlags()) c.help = flags.Usage(help, c.flags) + + // Deprecations + c.flags.StringVar(&c.tokenID, "id", "", + "DEPRECATED. Use -accessor-id instead.") } func (c *cmd) Run(args []string) int { @@ -43,9 +48,15 @@ func (c *cmd) Run(args []string) int { return 1 } - if c.tokenID == "" { - c.UI.Error(fmt.Sprintf("Must specify the -id parameter")) - return 1 + tokenAccessor := c.tokenAccessorID + if tokenAccessor == "" { + if c.tokenID == "" { + c.UI.Error("Must specify the -accessor-id parameter") + return 1 + } else { + tokenAccessor = c.tokenID + c.UI.Warn("Use the -accessor-id parameter to specify token by Accessor ID.") + } } client, err := c.http.APIClient() @@ -54,18 +65,18 @@ func (c *cmd) Run(args []string) int { return 1 } - tokenID, err := acl.GetTokenIDFromPartial(client, c.tokenID) + tok, err := acl.GetTokenAccessorIDFromPartial(client, tokenAccessor) if err != nil { c.UI.Error(fmt.Sprintf("Error determining token ID: %v", err)) return 1 } - if _, err := client.ACL().TokenDelete(tokenID, nil); err != nil { - c.UI.Error(fmt.Sprintf("Error deleting token %q: %v", tokenID, err)) + if _, err := client.ACL().TokenDelete(tok, nil); err != nil { + c.UI.Error(fmt.Sprintf("Error deleting token %q: %v", tok, err)) return 1 } - c.UI.Info(fmt.Sprintf("Token %q deleted successfully", tokenID)) + c.UI.Info(fmt.Sprintf("Token %q deleted successfully", tok)) return 0 } @@ -80,16 +91,16 @@ func (c *cmd) Help() string { const ( synopsis = "Delete an ACL token" help = ` -Usage: consul acl token delete [options] -id TOKEN +Usage: consul acl token delete [options] -accessor-id TOKEN Deletes an ACL token by providing either the ID or a unique ID prefix. Delete by prefix: - $ consul acl token delete -id b6b85 + $ consul acl token delete -accessor-id b6b85 Delete by full ID: - $ consul acl token delete -id b6b856da-5193-4e78-845a-7d61ca8371ba + $ consul acl token delete -accessor-id b6b856da-5193-4e78-845a-7d61ca8371ba ` ) diff --git a/command/acl/token/delete/token_delete_test.go b/command/acl/token/delete/token_delete_test.go index 5ce7117cb..be01fdf22 100644 --- a/command/acl/token/delete/token_delete_test.go +++ b/command/acl/token/delete/token_delete_test.go @@ -5,11 +5,12 @@ import ( "strings" "testing" + "github.com/mitchellh/cli" + "github.com/stretchr/testify/assert" + "github.com/hashicorp/consul/agent" "github.com/hashicorp/consul/api" "github.com/hashicorp/consul/testrpc" - "github.com/mitchellh/cli" - "github.com/stretchr/testify/assert" ) func TestTokenDeleteCommand_noTabs(t *testing.T) { @@ -54,7 +55,7 @@ func TestTokenDeleteCommand(t *testing.T) { args := []string{ "-http-addr=" + a.HTTPAddr(), "-token=root", - "-id=" + token.AccessorID, + "-accessor-id=" + token.AccessorID, } code := cmd.Run(args) diff --git a/command/acl/token/read/token_read.go b/command/acl/token/read/token_read.go index e5a3b87b0..79ee10f4f 100644 --- a/command/acl/token/read/token_read.go +++ b/command/acl/token/read/token_read.go @@ -25,11 +25,13 @@ type cmd struct { http *flags.HTTPFlags help string - tokenID string - self bool - showMeta bool - format string - expanded bool + tokenAccessorID string + self bool + showMeta bool + format string + expanded bool + + tokenID string // DEPRECATED } func (c *cmd) init() { @@ -37,10 +39,10 @@ func (c *cmd) init() { c.flags.BoolVar(&c.showMeta, "meta", false, "Indicates that token metadata such "+ "as the content hash and Raft indices should be shown for each entry") c.flags.BoolVar(&c.self, "self", false, "Indicates that the current HTTP token "+ - "should be read by secret ID instead of expecting a -id option") + "should be read by secret ID instead of expecting a -accessor-id option") c.flags.BoolVar(&c.expanded, "expanded", false, "Indicates that the contents of the "+ " policies and roles affecting the token should also be shown.") - c.flags.StringVar(&c.tokenID, "id", "", "The Accessor ID of the token to read. "+ + c.flags.StringVar(&c.tokenAccessorID, "accessor-id", "", "The Accessor ID of the token to read. "+ "It may be specified as a unique ID prefix but will error if the prefix "+ "matches multiple token Accessor IDs") c.flags.StringVar( @@ -54,6 +56,10 @@ func (c *cmd) init() { flags.Merge(c.flags, c.http.ServerFlags()) flags.Merge(c.flags, c.http.MultiTenancyFlags()) c.help = flags.Usage(help, c.flags) + + // Deprecations + c.flags.StringVar(&c.tokenID, "id", "", + "DEPRECATED. Use -accessor-id instead.") } func (c *cmd) Run(args []string) int { @@ -61,9 +67,15 @@ func (c *cmd) Run(args []string) int { return 1 } - if c.tokenID == "" && !c.self { - c.UI.Error(fmt.Sprintf("Must specify the -id parameter")) - return 1 + tokenAccessor := c.tokenAccessorID + if tokenAccessor == "" { + if c.tokenID == "" { + c.UI.Error("Must specify the -accessor-id parameter") + return 1 + } else { + tokenAccessor = c.tokenID + c.UI.Warn("Use the -accessor-id parameter to specify token by Accessor ID") + } } client, err := c.http.APIClient() @@ -75,27 +87,27 @@ func (c *cmd) Run(args []string) int { var t *api.ACLToken var expanded *api.ACLTokenExpanded if !c.self { - tokenID, err := acl.GetTokenIDFromPartial(client, c.tokenID) + tok, err := acl.GetTokenAccessorIDFromPartial(client, tokenAccessor) if err != nil { c.UI.Error(fmt.Sprintf("Error determining token ID: %v", err)) return 1 } if !c.expanded { - t, _, err = client.ACL().TokenRead(tokenID, nil) + t, _, err = client.ACL().TokenRead(tok, nil) } else { - expanded, _, err = client.ACL().TokenReadExpanded(tokenID, nil) + expanded, _, err = client.ACL().TokenReadExpanded(tok, nil) } if err != nil { - c.UI.Error(fmt.Sprintf("Error reading token %q: %v", tokenID, err)) + c.UI.Error(fmt.Sprintf("Error reading token %q: %v", tok, err)) return 1 } } else { // TODO: consider updating this CLI command and underlying HTTP API endpoint // to support expanded read of a "self" token, which is a much better user workflow. if c.expanded { - c.UI.Error("Cannot use both -expanded and -self. Instead, use -expanded and -id=.") + c.UI.Error("Cannot use both -expanded and -self. Instead, use -expanded and -accessor-id=.") return 1 } @@ -139,17 +151,17 @@ func (c *cmd) Help() string { const ( synopsis = "Read an ACL token" help = ` -Usage: consul acl token read [options] -id TOKENID +Usage: consul acl token read [options] -accessor-id TOKENID This command will retrieve and print out the details of a single token. Using a partial ID: - $ consul acl token read -id 4be56c77-82 + $ consul acl token read -accessor-id 4be56c77-82 Using the full ID: - $ consul acl token read -id 4be56c77-8244-4c7d-b08c-667b8c71baed + $ consul acl token read -accessor-id 4be56c77-8244-4c7d-b08c-667b8c71baed ` ) diff --git a/command/acl/token/read/token_read_test.go b/command/acl/token/read/token_read_test.go index f8c657298..505b15b02 100644 --- a/command/acl/token/read/token_read_test.go +++ b/command/acl/token/read/token_read_test.go @@ -6,12 +6,13 @@ import ( "strings" "testing" - "github.com/hashicorp/consul/agent" - "github.com/hashicorp/consul/api" - "github.com/hashicorp/consul/testrpc" "github.com/mitchellh/cli" "github.com/stretchr/testify/assert" "github.com/stretchr/testify/require" + + "github.com/hashicorp/consul/agent" + "github.com/hashicorp/consul/api" + "github.com/hashicorp/consul/testrpc" ) func TestTokenReadCommand_noTabs(t *testing.T) { @@ -56,7 +57,7 @@ func TestTokenReadCommand_Pretty(t *testing.T) { args := []string{ "-http-addr=" + a.HTTPAddr(), "-token=root", - "-id=" + token.AccessorID, + "-accessor-id=" + token.AccessorID, } code := cmd.Run(args) @@ -103,7 +104,7 @@ func TestTokenReadCommand_JSON(t *testing.T) { args := []string{ "-http-addr=" + a.HTTPAddr(), "-token=root", - "-id=" + token.AccessorID, + "-accessor-id=" + token.AccessorID, "-format=json", } diff --git a/command/acl/token/token.go b/command/acl/token/token.go index 4914f4dad..87ca60fd5 100644 --- a/command/acl/token/token.go +++ b/command/acl/token/token.go @@ -1,8 +1,9 @@ package token import ( - "github.com/hashicorp/consul/command/flags" "github.com/mitchellh/cli" + + "github.com/hashicorp/consul/command/flags" ) func New() *cmd { @@ -42,15 +43,15 @@ Usage: consul acl token [options] [args] Update a token: - $ consul acl token update -id 986193 -description "WonderToken" + $ consul acl token update -accessor-id 986193 -description "WonderToken" Read a token with an accessor ID: - $ consul acl token read -id 986193 + $ consul acl token read -accessor-id 986193 Delete a token - $ consul acl token delete -id 986193 + $ consul acl token delete -accessor-id 986193 For more examples, ask for subcommand help or view the documentation. ` diff --git a/command/acl/token/update/token_update.go b/command/acl/token/update/token_update.go index ad8d613a6..4f168e927 100644 --- a/command/acl/token/update/token_update.go +++ b/command/acl/token/update/token_update.go @@ -25,7 +25,7 @@ type cmd struct { http *flags.HTTPFlags help string - tokenID string + tokenAccessorID string policyIDs []string policyNames []string roleIDs []string @@ -39,6 +39,8 @@ type cmd struct { mergeNodeIdents bool showMeta bool format string + + tokenID string // DEPRECATED } func (c *cmd) init() { @@ -53,7 +55,7 @@ func (c *cmd) init() { "with the existing service identities") c.flags.BoolVar(&c.mergeNodeIdents, "merge-node-identities", false, "Merge the new node identities "+ "with the existing node identities") - c.flags.StringVar(&c.tokenID, "id", "", "The Accessor ID of the token to update. "+ + c.flags.StringVar(&c.tokenAccessorID, "accessor-id", "", "The Accessor ID of the token to update. "+ "It may be specified as a unique ID prefix but will error if the prefix "+ "matches multiple token Accessor IDs") c.flags.StringVar(&c.description, "description", "", "A description of the token") @@ -83,6 +85,10 @@ func (c *cmd) init() { flags.Merge(c.flags, c.http.ServerFlags()) flags.Merge(c.flags, c.http.MultiTenancyFlags()) c.help = flags.Usage(help, c.flags) + + // Deprecations + c.flags.StringVar(&c.tokenID, "id", "", + "DEPRECATED. Use -accessor-id instead.") } func (c *cmd) Run(args []string) int { @@ -90,9 +96,15 @@ func (c *cmd) Run(args []string) int { return 1 } - if c.tokenID == "" { - c.UI.Error(fmt.Sprintf("Cannot update a token without specifying the -id parameter")) - return 1 + tokenAccessor := c.tokenAccessorID + if tokenAccessor == "" { + if c.tokenID == "" { + c.UI.Error("Cannot update a token without specifying the -accessor-id parameter") + return 1 + } else { + tokenAccessor = c.tokenID + c.UI.Warn("Use the -accessor-id parameter to specify token by Accessor ID") + } } client, err := c.http.APIClient() @@ -101,13 +113,13 @@ func (c *cmd) Run(args []string) int { return 1 } - tokenID, err := acl.GetTokenIDFromPartial(client, c.tokenID) + tok, err := acl.GetTokenAccessorIDFromPartial(client, tokenAccessor) if err != nil { c.UI.Error(fmt.Sprintf("Error determining token ID: %v", err)) return 1 } - t, _, err := client.ACL().TokenRead(tokenID, nil) + t, _, err := client.ACL().TokenRead(tok, nil) if err != nil { c.UI.Error(fmt.Sprintf("Error when retrieving current token: %v", err)) return 1 @@ -285,7 +297,7 @@ func (c *cmd) Run(args []string) int { t, _, err = client.ACL().TokenUpdate(t, nil) if err != nil { - c.UI.Error(fmt.Sprintf("Failed to update token %s: %v", tokenID, err)) + c.UI.Error(fmt.Sprintf("Failed to update token %s: %v", tok, err)) return 1 } @@ -324,11 +336,11 @@ Usage: consul acl token update [options] Update a token description and take the policies from the existing token: - $ consul acl token update -id abcd -description "replication" -merge-policies + $ consul acl token update -accessor-id abcd -description "replication" -merge-policies Update all editable fields of the token: - $ consul acl token update -id abcd \ + $ consul acl token update -accessor-id abcd \ -description "replication" \ -policy-name "token-replication" \ -role-name "db-updater" diff --git a/command/acl/token/update/token_update_test.go b/command/acl/token/update/token_update_test.go index 1117c1104..541d1e225 100644 --- a/command/acl/token/update/token_update_test.go +++ b/command/acl/token/update/token_update_test.go @@ -74,7 +74,7 @@ func TestTokenUpdateCommand(t *testing.T) { t.Run("node-identity", func(t *testing.T) { token := run(t, []string{ "-http-addr=" + a.HTTPAddr(), - "-id=" + token.AccessorID, + "-accessor-id=" + token.AccessorID, "-token=root", "-node-identity=foo:bar", "-description=test token", @@ -88,7 +88,7 @@ func TestTokenUpdateCommand(t *testing.T) { t.Run("node-identity-merge", func(t *testing.T) { token := run(t, []string{ "-http-addr=" + a.HTTPAddr(), - "-id=" + token.AccessorID, + "-accessor-id=" + token.AccessorID, "-token=root", "-node-identity=bar:baz", "-description=test token", @@ -113,7 +113,7 @@ func TestTokenUpdateCommand(t *testing.T) { t.Run("policy-name", func(t *testing.T) { token := run(t, []string{ "-http-addr=" + a.HTTPAddr(), - "-id=" + token.AccessorID, + "-accessor-id=" + token.AccessorID, "-token=root", "-policy-name=" + policy.Name, "-description=test token", @@ -126,7 +126,7 @@ func TestTokenUpdateCommand(t *testing.T) { t.Run("policy-id", func(t *testing.T) { token := run(t, []string{ "-http-addr=" + a.HTTPAddr(), - "-id=" + token.AccessorID, + "-accessor-id=" + token.AccessorID, "-token=root", "-policy-id=" + policy.ID, "-description=test token", @@ -139,7 +139,7 @@ func TestTokenUpdateCommand(t *testing.T) { t.Run("merge-description", func(t *testing.T) { token := run(t, []string{ "-http-addr=" + a.HTTPAddr(), - "-id=" + token.AccessorID, + "-accessor-id=" + token.AccessorID, "-token=root", "-policy-name=" + policy.Name, }) @@ -189,7 +189,7 @@ func TestTokenUpdateCommand_JSON(t *testing.T) { cmd := New(ui) args := []string{ "-http-addr=" + a.HTTPAddr(), - "-id=" + token.AccessorID, + "-accessor-id=" + token.AccessorID, "-token=root", "-policy-name=" + policy.Name, "-description=test token", diff --git a/website/content/docs/security/acl/acl-tokens.mdx b/website/content/docs/security/acl/acl-tokens.mdx index bb239e1a8..da14d52d8 100644 --- a/website/content/docs/security/acl/acl-tokens.mdx +++ b/website/content/docs/security/acl/acl-tokens.mdx @@ -143,7 +143,6 @@ Refer to the [API](/consul/api-docs/acl/tokens) or [command line](/consul/comman | `Local` | Indicates whether the token should be replicated globally or local to the datacenter.
Set to `false` to replicate globally across all reachable datacenters.
Setting to `true` configures the token to functional in the local datacenter only. | Boolean | `false` | | `ServiceIdentities` | Specifies a list of service identities to apply to the token. See [Service Identities](/consul/docs/security/acl/acl-roles#service-identities) in the "Roles" topic for additional information. | Array | none | | `NodeIdentities` | Specifies a list of node identities to apply to the token. See [Node Identities](/consul/docs/security/acl/acl-roles#node-identities) in the "Roles" topic for additional information. | Array | none | -| `Legacy` | Indicates if the token was created using the the legacy ACL system. | Boolean | `false` | | `Policies` | List of policies linked to the token, including the policy ID and name. | String | none | | `Roles` | List of roles linked to the token, including the role ID and name. | String | none |