зеркало из https://github.com/getsops/sops.git
Rename Cloud KMS to GCP KMS
This commit is contained in:
Родитель
f57598d02c
Коммит
f7d72449b2
2
Makefile
2
Makefile
|
@ -33,7 +33,7 @@ test:
|
|||
gpg --import pgp/sops_functional_tests_key.asc 2>&1 1>/dev/null || exit 0
|
||||
$(GO) test $(PROJECT)/pgp -coverprofile=coverage_tmp.txt -covermode=atomic && cat coverage_tmp.txt >> coverage.txt
|
||||
$(GO) test $(PROJECT)/kms -coverprofile=coverage_tmp.txt -covermode=atomic && cat coverage_tmp.txt >> coverage.txt
|
||||
$(GO) test $(PROJECT)/cloudkms -coverprofile=coverage_tmp.txt -covermode=atomic && cat coverage_tmp.txt >> coverage.txt
|
||||
$(GO) test $(PROJECT)/gcpkms -coverprofile=coverage_tmp.txt -covermode=atomic && cat coverage_tmp.txt >> coverage.txt
|
||||
|
||||
showcoverage: test
|
||||
$(GO) tool cover -html=coverage.out
|
||||
|
|
|
@ -21,7 +21,7 @@ import (
|
|||
"github.com/google/shlex"
|
||||
|
||||
"go.mozilla.org/sops/aes"
|
||||
"go.mozilla.org/sops/cloudkms"
|
||||
"go.mozilla.org/sops/gcpkms"
|
||||
"go.mozilla.org/sops/json"
|
||||
"go.mozilla.org/sops/kms"
|
||||
"go.mozilla.org/sops/pgp"
|
||||
|
@ -92,7 +92,7 @@ func main() {
|
|||
cli.VersionPrinter = printVersion
|
||||
app := cli.NewApp()
|
||||
app.Name = "sops"
|
||||
app.Usage = "sops - encrypted file editor with AWS KMS, google cloud KMS and GPG support"
|
||||
app.Usage = "sops - encrypted file editor with AWS KMS, GCP KMS and GPG support"
|
||||
app.ArgsUsage = "sops [options] file"
|
||||
app.Version = version
|
||||
app.Authors = []cli.Author{
|
||||
|
@ -105,8 +105,8 @@ func main() {
|
|||
in the -k flag or in the SOPS_KMS_ARN environment variable.
|
||||
(you need valid credentials in ~/.aws/credentials or in your env)
|
||||
|
||||
To encrypt or decrypt a document with google cloud KMS, specify the
|
||||
cloud KMS resource Id in the -c flag or in the SOPS_CLOUD_KMS_IDS
|
||||
To encrypt or decrypt a document with GCP KMS, specify the
|
||||
GCP KMS resource ID in the --gcp-kms flag or in the SOPS_GCP_KMS_IDS
|
||||
environment variable.
|
||||
(you need to setup google application default credentials. See
|
||||
https://developers.google.com/identity/protocols/application-default-credentials)
|
||||
|
@ -121,7 +121,7 @@ func main() {
|
|||
decrypting existing documents can be done with "sops file" or
|
||||
"sops -d file" respectively. The KMS and PGP keys listed in the encrypted
|
||||
documents are used then. To manage master keys in existing documents, use
|
||||
the "add-{kms,pgp,cloud-kms}" and "rm-{kms,pgp,cloud-kms}" flags.
|
||||
the "add-{kms,pgp,gcp-kms}" and "rm-{kms,pgp,gcp-kms}" flags.
|
||||
|
||||
To use a different GPG binary than the one in your PATH, set SOPS_GPG_EXEC.
|
||||
|
||||
|
@ -148,9 +148,9 @@ func main() {
|
|||
EnvVar: "SOPS_KMS_ARN",
|
||||
},
|
||||
cli.StringFlag{
|
||||
Name: "cloud-kms, c",
|
||||
Usage: "comma separated list of google cloud KMS resource IDs",
|
||||
EnvVar: "SOPS_CLOUD_KMS_IDS",
|
||||
Name: "gcp-kms",
|
||||
Usage: "comma separated list of GCP KMS resource IDs",
|
||||
EnvVar: "SOPS_CGP_KMS_IDS",
|
||||
},
|
||||
cli.StringFlag{
|
||||
Name: "pgp, p",
|
||||
|
@ -178,12 +178,12 @@ func main() {
|
|||
Usage: "display master encryption keys in the file during editing",
|
||||
},
|
||||
cli.StringFlag{
|
||||
Name: "add-cloud-kms",
|
||||
Usage: "add the provided comma-separated list of google cloud KMS key resource IDs to the list of master keys on the given file",
|
||||
Name: "add-gcp-kms",
|
||||
Usage: "add the provided comma-separated list of GCP KMS key resource IDs to the list of master keys on the given file",
|
||||
},
|
||||
cli.StringFlag{
|
||||
Name: "rm-cloud-kms",
|
||||
Usage: "remove the provided comma-separated list of google cloud KMS key resource IDs from the list of master keys on the given file",
|
||||
Name: "rm-gcp-kms",
|
||||
Usage: "remove the provided comma-separated list of GCP KMS key resource IDs from the list of master keys on the given file",
|
||||
},
|
||||
cli.StringFlag{
|
||||
Name: "add-kms",
|
||||
|
@ -230,7 +230,7 @@ func main() {
|
|||
}
|
||||
fileName := c.Args()[0]
|
||||
if _, err := os.Stat(fileName); os.IsNotExist(err) {
|
||||
if c.String("add-kms") != "" || c.String("add-pgp") != "" || c.String("add-cloud-kms") != "" || c.String("rm-kms") != "" || c.String("rm-pgp") != "" || c.String("rm-cloud-kms") != "" {
|
||||
if c.String("add-kms") != "" || c.String("add-pgp") != "" || c.String("add-gcp-kms") != "" || c.String("rm-kms") != "" || c.String("rm-pgp") != "" || c.String("rm-gcp-kms") != "" {
|
||||
return cli.NewExitError("Error: cannot add or remove keys on non-existent files, use `--kms` and `--pgp` instead.", 49)
|
||||
}
|
||||
if c.Bool("encrypt") || c.Bool("decrypt") || c.Bool("rotate") {
|
||||
|
@ -423,8 +423,8 @@ func getKeySources(c *cli.Context, file string) ([]sops.KeySource, error) {
|
|||
kmsKeys = append(kmsKeys, k)
|
||||
}
|
||||
}
|
||||
if c.String("cloud-kms") != "" {
|
||||
for _, k := range cloudkms.MasterKeysFromResourceIdString(c.String("cloud-kms")) {
|
||||
if c.String("gcp-kms") != "" {
|
||||
for _, k := range gcpkms.MasterKeysFromResourceIdString(c.String("gcp-kms")) {
|
||||
cloudKmsKeys = append(cloudKmsKeys, k)
|
||||
}
|
||||
}
|
||||
|
@ -434,7 +434,7 @@ func getKeySources(c *cli.Context, file string) ([]sops.KeySource, error) {
|
|||
}
|
||||
}
|
||||
var err error
|
||||
if c.String("kms") == "" && c.String("pgp") == "" && c.String("cloud-kms") == "" {
|
||||
if c.String("kms") == "" && c.String("pgp") == "" && c.String("gcp-kms") == "" {
|
||||
var confBytes []byte
|
||||
if c.String("config") != "" {
|
||||
confBytes, err = ioutil.ReadFile(c.String("config"))
|
||||
|
@ -454,7 +454,7 @@ func getKeySources(c *cli.Context, file string) ([]sops.KeySource, error) {
|
|||
}
|
||||
kmsKs := sops.KeySource{Name: "kms", Keys: kmsKeys}
|
||||
pgpKs := sops.KeySource{Name: "pgp", Keys: pgpKeys}
|
||||
cloudKmsKs := sops.KeySource{Name: "cloud-kms", Keys: cloudKmsKeys}
|
||||
cloudKmsKs := sops.KeySource{Name: "gcp_kms", Keys: cloudKmsKeys}
|
||||
return []sops.KeySource{kmsKs, cloudKmsKs, pgpKs}, nil
|
||||
}
|
||||
|
||||
|
@ -500,10 +500,10 @@ func rotate(c *cli.Context, tree sops.Tree, outputStore sops.Store) ([]byte, err
|
|||
}
|
||||
tree.Metadata.AddKMSMasterKeys(c.String("add-kms"), kmsEncryptionContext)
|
||||
tree.Metadata.AddPGPMasterKeys(c.String("add-pgp"))
|
||||
tree.Metadata.AddCloudKMSMasterKeys(c.String("add-cloud-kms"))
|
||||
tree.Metadata.AddGCPKMSMasterKeys(c.String("add-gcp-kms"))
|
||||
tree.Metadata.RemoveKMSMasterKeys(c.String("rm-kms"))
|
||||
tree.Metadata.RemovePGPMasterKeys(c.String("rm-pgp"))
|
||||
tree.Metadata.RemoveCloudKMSMasterKeys(c.String("rm-cloud-kms"))
|
||||
tree.Metadata.RemoveGCPKMSMasterKeys(c.String("rm-gcp-kms"))
|
||||
_, errs := tree.GenerateDataKey()
|
||||
if len(errs) > 0 {
|
||||
return nil, cli.NewExitError(fmt.Sprintf("Error encrypting the data key with one or more master keys: %s", errs), exitCouldNotRetrieveKey)
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
package cloudkms //import "go.mozilla.org/sops/cloudkms"
|
||||
package gcpkms //import "go.mozilla.org/sops/gcpkms"
|
||||
|
||||
import (
|
||||
"encoding/base64"
|
||||
|
@ -13,30 +13,25 @@ import (
|
|||
cloudkms "google.golang.org/api/cloudkms/v1"
|
||||
)
|
||||
|
||||
// this needs to be a global var for unit tests to work (mockKMS redefines
|
||||
// it in keysource_test.go)
|
||||
// var kmsSvc kmsiface.KMSAPI
|
||||
// var isMocked bool
|
||||
|
||||
// MasterKey is a cloud KMS key used to encrypt and decrypt sops' data key.
|
||||
// MasterKey is a GCP KMS key used to encrypt and decrypt sops' data key.
|
||||
type MasterKey struct {
|
||||
ResourceId string
|
||||
EncryptedKey string
|
||||
CreationDate time.Time
|
||||
}
|
||||
|
||||
// Encrypt takes a sops data key, encrypts it with cloud KMS and stores the result in the EncryptedKey field
|
||||
// Encrypt takes a sops data key, encrypts it with GCP KMS and stores the result in the EncryptedKey field
|
||||
func (key *MasterKey) Encrypt(dataKey []byte) error {
|
||||
cloudkmsService, err := key.createCloudKMSService()
|
||||
if err != nil {
|
||||
return fmt.Errorf("Cannot create cloud KMS service: %v", err)
|
||||
return fmt.Errorf("Cannot create GCP KMS service: %v", err)
|
||||
}
|
||||
req := &cloudkms.EncryptRequest{
|
||||
Plaintext: base64.StdEncoding.EncodeToString(dataKey),
|
||||
}
|
||||
resp, err := cloudkmsService.Projects.Locations.KeyRings.CryptoKeys.Encrypt(key.ResourceId, req).Do()
|
||||
if err != nil {
|
||||
return fmt.Errorf("Failed to call cloud KMS encryption service: %v", err)
|
||||
return fmt.Errorf("Failed to call GCP KMS encryption service: %v", err)
|
||||
}
|
||||
|
||||
key.EncryptedKey = resp.Ciphertext
|
||||
|
@ -51,11 +46,11 @@ func (key *MasterKey) EncryptIfNeeded(dataKey []byte) error {
|
|||
return nil
|
||||
}
|
||||
|
||||
// Decrypt decrypts the EncryptedKey field with cloud KMS and returns the result.
|
||||
// Decrypt decrypts the EncryptedKey field with CGP KMS and returns the result.
|
||||
func (key *MasterKey) Decrypt() ([]byte, error) {
|
||||
cloudkmsService, err := key.createCloudKMSService()
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("Cannot create cloud KMS service: %v", err)
|
||||
return nil, fmt.Errorf("Cannot create GCP KMS service: %v", err)
|
||||
}
|
||||
|
||||
req := &cloudkms.DecryptRequest{
|
||||
|
@ -78,7 +73,7 @@ func (key *MasterKey) ToString() string {
|
|||
return key.ResourceId
|
||||
}
|
||||
|
||||
// NewMasterKeyFromResourceId takes an cloud KMS resource id string and returns a new MasterKey for that
|
||||
// NewMasterKeyFromResourceId takes a GCP KMS resource ID string and returns a new MasterKey for that
|
||||
func NewMasterKeyFromResourceId(resourceId string) *MasterKey {
|
||||
k := &MasterKey{}
|
||||
resourceId = strings.Replace(resourceId, " ", "", -1)
|
||||
|
@ -87,8 +82,7 @@ func NewMasterKeyFromResourceId(resourceId string) *MasterKey {
|
|||
return k
|
||||
}
|
||||
|
||||
// MasterKeysFromResourceIdString takes a comma separated list of cloud KMS
|
||||
// resourece IDs and returns a slice of new MasterKeys for them
|
||||
// MasterKeysFromResourceIdString takes a comma separated list of GCP KMS resourece IDs and returns a slice of new MasterKeys for them
|
||||
func MasterKeysFromResourceIdString(resourceId string) []*MasterKey {
|
||||
var keys []*MasterKey
|
||||
if resourceId == "" {
|
|
@ -1,4 +1,4 @@
|
|||
package cloudkms
|
||||
package gcpkms
|
||||
|
||||
import (
|
||||
"testing"
|
||||
|
@ -7,7 +7,7 @@ import (
|
|||
"github.com/stretchr/testify/assert"
|
||||
)
|
||||
|
||||
func TestCloudKMSKeySourceFromString(t *testing.T) {
|
||||
func TestGCPKMSKeySourceFromString(t *testing.T) {
|
||||
s := "projects/sops-testing1/locations/global/keyRings/creds/cryptoKeys/key1, projects/sops-testing2/locations/global/keyRings/creds/cryptoKeys/key2"
|
||||
ks := MasterKeysFromResourceIdString(s)
|
||||
k1 := ks[0]
|
32
sops.go
32
sops.go
|
@ -43,7 +43,7 @@ import (
|
|||
"strings"
|
||||
"time"
|
||||
|
||||
"go.mozilla.org/sops/cloudkms"
|
||||
"go.mozilla.org/sops/gcpkms"
|
||||
"go.mozilla.org/sops/kms"
|
||||
"go.mozilla.org/sops/pgp"
|
||||
)
|
||||
|
@ -386,14 +386,14 @@ func (m *Metadata) AddPGPMasterKeys(pgpFps string) {
|
|||
}
|
||||
}
|
||||
|
||||
// AddCloudKMSMasterKeys parses the input comma separated string of cloud KMS resource IDs, generates a KMS MasterKey for each resource ID, and then adds the keys to the cloud KMS KeySource
|
||||
func (m *Metadata) AddCloudKMSMasterKeys(resourceIds string) {
|
||||
// AddGCPKMSMasterKeys parses the input comma separated string of GCP KMS resource IDs, generates a MasterKey for each resource ID, and then adds the keys to the GCP KMS KeySource
|
||||
func (m *Metadata) AddGCPKMSMasterKeys(resourceIds string) {
|
||||
for i, ks := range m.KeySources {
|
||||
if ks.Name == "cloud-kms" {
|
||||
if ks.Name == "gcp_kms" {
|
||||
var keys []MasterKey
|
||||
for _, k := range cloudkms.MasterKeysFromResourceIdString(resourceIds) {
|
||||
for _, k := range gcpkms.MasterKeysFromResourceIdString(resourceIds) {
|
||||
keys = append(keys, k)
|
||||
fmt.Printf("Adding new cloud KMS master key: %s\n", k.ResourceId)
|
||||
fmt.Printf("Adding new GCP KMS master key: %s\n", k.ResourceId)
|
||||
}
|
||||
ks.Keys = append(ks.Keys, keys...)
|
||||
m.KeySources[i] = ks
|
||||
|
@ -434,10 +434,10 @@ func (m *Metadata) RemoveKMSMasterKeys(arns string) {
|
|||
m.RemoveMasterKeys(keys)
|
||||
}
|
||||
|
||||
// RemoveCloudKMSMasterKeys takes a comma separated string of cloud KMS resource IDs and removes the corresponding keys
|
||||
func (m *Metadata) RemoveCloudKMSMasterKeys(resourceIds string) {
|
||||
// RemoveGCPKMSMasterKeys takes a comma separated string of GCP KMS resource IDs and removes the corresponding keys
|
||||
func (m *Metadata) RemoveGCPKMSMasterKeys(resourceIds string) {
|
||||
var keys []MasterKey
|
||||
for _, k := range cloudkms.MasterKeysFromResourceIdString(resourceIds) {
|
||||
for _, k := range gcpkms.MasterKeysFromResourceIdString(resourceIds) {
|
||||
keys = append(keys, k)
|
||||
}
|
||||
m.RemoveMasterKeys(keys)
|
||||
|
@ -472,6 +472,8 @@ func (m Metadata) GetDataKey() ([]byte, error) {
|
|||
keyType := "Unknown"
|
||||
if _, ok := k.(*pgp.MasterKey); ok {
|
||||
keyType = "GPG"
|
||||
} else if _, ok := k.(*gcpkms.MasterKey); ok {
|
||||
keyType = "GCP KMS"
|
||||
} else if _, ok := k.(*kms.MasterKey); ok {
|
||||
keyType = "KMS"
|
||||
}
|
||||
|
@ -528,8 +530,8 @@ func MapToMetadata(data map[string]interface{}) (Metadata, error) {
|
|||
}
|
||||
}
|
||||
|
||||
if cloudk, ok := data["cloud-kms"].([]interface{}); ok {
|
||||
ks, err := mapCloudKMSEntriesToKeySource(cloudk)
|
||||
if gcpk, ok := data["gcp_kms"].([]interface{}); ok {
|
||||
ks, err := mapGCPKMSEntriesToKeySource(gcpk)
|
||||
if err == nil {
|
||||
metadata.KeySources = append(metadata.KeySources, ks)
|
||||
}
|
||||
|
@ -556,9 +558,9 @@ func convertToMapStringInterface(in map[interface{}]interface{}) (map[string]int
|
|||
return m, nil
|
||||
}
|
||||
|
||||
func mapCloudKMSEntriesToKeySource(in []interface{}) (KeySource, error) {
|
||||
func mapGCPKMSEntriesToKeySource(in []interface{}) (KeySource, error) {
|
||||
var keys []MasterKey
|
||||
keysource := KeySource{Name: "cloud-kms", Keys: keys}
|
||||
keysource := KeySource{Name: "gcp_kms", Keys: keys}
|
||||
for _, v := range in {
|
||||
entry, ok := v.(map[string]interface{})
|
||||
if !ok {
|
||||
|
@ -566,11 +568,11 @@ func mapCloudKMSEntriesToKeySource(in []interface{}) (KeySource, error) {
|
|||
var err error
|
||||
entry, err = convertToMapStringInterface(m)
|
||||
if !ok || err != nil {
|
||||
fmt.Println("Cloud KMS entry has invalid format, skipping...")
|
||||
fmt.Println("GCP KMS entry has invalid format, skipping...")
|
||||
continue
|
||||
}
|
||||
}
|
||||
key := &cloudkms.MasterKey{}
|
||||
key := &gcpkms.MasterKey{}
|
||||
key.ResourceId = entry["resource_id"].(string)
|
||||
key.EncryptedKey = entry["enc"].(string)
|
||||
creationDate, err := time.Parse(time.RFC3339, entry["created_at"].(string))
|
||||
|
|
Загрузка…
Ссылка в новой задаче