mirror of
https://github.com/hashicorp/vault.git
synced 2025-08-11 17:17:01 +02:00
* Add AWS Secret Engine Root Credential Rotation This allows the AWS Secret Engine to rotate its credentials used to access AWS. This will only work when the AWS Secret Engine has been provided explicit IAM credentials via the config/root endpoint, and further, when the IAM credentials provided are the only access key on the IAM user associated wtih the access key (because AWS allows a maximum of 2 access keys per user). Fixes #4385 * Add test for AWS root credential rotation Also fix a typo in the root credential rotation code * Add docs for AWS root rotation * Add locks around reading and writing config/root And wire the backend up in a bunch of places so the config can get the lock * Respond to PR feedback * Fix casing in error messages * Fix merge errors * Fix locking bugs
105 lines
3.0 KiB
Go
105 lines
3.0 KiB
Go
package aws
|
|
|
|
import (
|
|
"context"
|
|
|
|
"github.com/aws/aws-sdk-go/aws"
|
|
"github.com/hashicorp/vault/logical"
|
|
"github.com/hashicorp/vault/logical/framework"
|
|
)
|
|
|
|
func pathConfigRoot(b *backend) *framework.Path {
|
|
return &framework.Path{
|
|
Pattern: "config/root",
|
|
Fields: map[string]*framework.FieldSchema{
|
|
"access_key": &framework.FieldSchema{
|
|
Type: framework.TypeString,
|
|
Description: "Access key with permission to create new keys.",
|
|
},
|
|
|
|
"secret_key": &framework.FieldSchema{
|
|
Type: framework.TypeString,
|
|
Description: "Secret key with permission to create new keys.",
|
|
},
|
|
|
|
"region": &framework.FieldSchema{
|
|
Type: framework.TypeString,
|
|
Description: "Region for API calls.",
|
|
},
|
|
"iam_endpoint": &framework.FieldSchema{
|
|
Type: framework.TypeString,
|
|
Description: "Endpoint to custom IAM server URL",
|
|
},
|
|
"sts_endpoint": &framework.FieldSchema{
|
|
Type: framework.TypeString,
|
|
Description: "Endpoint to custom STS server URL",
|
|
},
|
|
"max_retries": &framework.FieldSchema{
|
|
Type: framework.TypeInt,
|
|
Default: aws.UseServiceDefaultRetries,
|
|
Description: "Maximum number of retries for recoverable exceptions of AWS APIs",
|
|
},
|
|
},
|
|
|
|
Callbacks: map[logical.Operation]framework.OperationFunc{
|
|
logical.UpdateOperation: b.pathConfigRootWrite,
|
|
},
|
|
|
|
HelpSynopsis: pathConfigRootHelpSyn,
|
|
HelpDescription: pathConfigRootHelpDesc,
|
|
}
|
|
}
|
|
|
|
func (b *backend) pathConfigRootWrite(ctx context.Context, req *logical.Request, data *framework.FieldData) (*logical.Response, error) {
|
|
region := data.Get("region").(string)
|
|
iamendpoint := data.Get("iam_endpoint").(string)
|
|
stsendpoint := data.Get("sts_endpoint").(string)
|
|
maxretries := data.Get("max_retries").(int)
|
|
|
|
b.clientMutex.Lock()
|
|
defer b.clientMutex.Unlock()
|
|
|
|
entry, err := logical.StorageEntryJSON("config/root", rootConfig{
|
|
AccessKey: data.Get("access_key").(string),
|
|
SecretKey: data.Get("secret_key").(string),
|
|
IAMEndpoint: iamendpoint,
|
|
STSEndpoint: stsendpoint,
|
|
Region: region,
|
|
MaxRetries: maxretries,
|
|
})
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
|
|
if err := req.Storage.Put(ctx, entry); err != nil {
|
|
return nil, err
|
|
}
|
|
|
|
// clear possible cached IAM / STS clients after successfully updating
|
|
// config/root
|
|
b.iamClient = nil
|
|
b.stsClient = nil
|
|
|
|
return nil, nil
|
|
}
|
|
|
|
type rootConfig struct {
|
|
AccessKey string `json:"access_key"`
|
|
SecretKey string `json:"secret_key"`
|
|
IAMEndpoint string `json:"iam_endpoint"`
|
|
STSEndpoint string `json:"sts_endpoint"`
|
|
Region string `json:"region"`
|
|
MaxRetries int `json:"max_retries"`
|
|
}
|
|
|
|
const pathConfigRootHelpSyn = `
|
|
Configure the root credentials that are used to manage IAM.
|
|
`
|
|
|
|
const pathConfigRootHelpDesc = `
|
|
Before doing anything, the AWS backend needs credentials that are able
|
|
to manage IAM policies, users, access keys, etc. This endpoint is used
|
|
to configure those credentials. They don't necessarily need to be root
|
|
keys as long as they have permission to manage IAM.
|
|
`
|