96 lines
2.1 KiB
Go
96 lines
2.1 KiB
Go
// Copyright (c) HashiCorp, Inc.
|
|
// SPDX-License-Identifier: MPL-2.0
|
|
|
|
package helm
|
|
|
|
import (
|
|
"encoding/json"
|
|
"fmt"
|
|
"strings"
|
|
|
|
"golang.org/x/crypto/sha3"
|
|
|
|
corev1 "k8s.io/api/core/v1"
|
|
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
|
"sigs.k8s.io/yaml"
|
|
|
|
"helm.sh/helm/v3/pkg/releaseutil"
|
|
)
|
|
|
|
type resourceMeta struct {
|
|
metav1.TypeMeta
|
|
Metadata metav1.ObjectMeta
|
|
}
|
|
|
|
func convertYAMLManifestToJSON(manifest string) (string, error) {
|
|
m := map[string]json.RawMessage{}
|
|
|
|
resources := releaseutil.SplitManifests(manifest)
|
|
for _, resource := range resources {
|
|
jsonbytes, err := yaml.YAMLToJSON([]byte(resource))
|
|
if err != nil {
|
|
return "", fmt.Errorf("could not convert manifest to JSON: %v", err)
|
|
}
|
|
|
|
resourceMeta := resourceMeta{}
|
|
err = yaml.Unmarshal([]byte(resource), &resourceMeta)
|
|
if err != nil {
|
|
return "", err
|
|
}
|
|
|
|
gvk := resourceMeta.GetObjectKind().GroupVersionKind()
|
|
key := fmt.Sprintf("%s/%s/%s", strings.ToLower(gvk.GroupKind().String()),
|
|
resourceMeta.APIVersion,
|
|
resourceMeta.Metadata.Name)
|
|
|
|
if namespace := resourceMeta.Metadata.Namespace; namespace != "" {
|
|
key = fmt.Sprintf("%s/%s", namespace, key)
|
|
}
|
|
|
|
if gvk.Kind == "Secret" {
|
|
secret := corev1.Secret{}
|
|
err = yaml.Unmarshal([]byte(resource), &secret)
|
|
if err != nil {
|
|
return "", err
|
|
}
|
|
|
|
for k, v := range secret.Data {
|
|
h := hashSensitiveValue(string(v))
|
|
secret.Data[k] = []byte(h)
|
|
}
|
|
|
|
jsonbytes, err = json.Marshal(secret)
|
|
if err != nil {
|
|
return "", err
|
|
}
|
|
}
|
|
|
|
m[key] = jsonbytes
|
|
}
|
|
|
|
b, err := json.Marshal(m)
|
|
if err != nil {
|
|
return "", err
|
|
}
|
|
|
|
return string(b), nil
|
|
}
|
|
|
|
func hashSensitiveValue(v string) string {
|
|
hash := make([]byte, 8)
|
|
sha3.ShakeSum256(hash, []byte(v))
|
|
return fmt.Sprintf("(sensitive value %x)", hash)
|
|
}
|
|
|
|
// redactSensitiveValues removes values that appear in `set_sensitive` blocks from the manifest JSON
|
|
func redactSensitiveValues(text string, sensitiveValues map[string]string) string {
|
|
masked := text
|
|
|
|
for originalValue := range sensitiveValues {
|
|
hashedValue := hashSensitiveValue(originalValue)
|
|
masked = strings.ReplaceAll(masked, originalValue, hashedValue)
|
|
}
|
|
|
|
return masked
|
|
}
|