github.com/tilt-dev/tilt@v0.33.15-0.20240515162809-0a22ed45d8a0/internal/controllers/core/kubernetesapply/hash.go (about) 1 package kubernetesapply 2 3 import ( 4 "crypto" 5 "encoding/base64" 6 "fmt" 7 "hash" 8 9 jsoniter "github.com/json-iterator/go" 10 "github.com/pkg/errors" 11 "k8s.io/apimachinery/pkg/types" 12 13 "github.com/tilt-dev/tilt/pkg/apis/core/v1alpha1" 14 ) 15 16 var defaultJSONIterator = createDefaultJSONIterator() 17 18 func createDefaultJSONIterator() jsoniter.API { 19 return jsoniter.Config{ 20 EscapeHTML: true, 21 SortMapKeys: true, 22 ValidateJsonRawMessage: true, 23 CaseSensitive: true, 24 }.Froze() 25 } 26 27 // Compute the hash of all the inputs we fed into this apply. 28 func ComputeInputHash(spec v1alpha1.KubernetesApplySpec, imageMaps map[types.NamespacedName]*v1alpha1.ImageMap) (string, error) { 29 w := newHashWriter() 30 err := w.append(spec) 31 if err != nil { 32 return "", err 33 } 34 35 for _, imageMapName := range spec.ImageMaps { 36 imageMap, ok := imageMaps[types.NamespacedName{Name: imageMapName}] 37 if !ok { 38 return "", fmt.Errorf("missing image map: %v", err) 39 } 40 err = w.append(imageMap.Spec) 41 if err != nil { 42 return "", fmt.Errorf("hashing %s spec: %v", imageMapName, err) 43 } 44 45 // Don't hash in the BuildStartedTime, because 46 // this changes even when the image does not change. 47 status := imageMap.Status 48 status.BuildStartTime = nil 49 err = w.append(status) 50 if err != nil { 51 return "", fmt.Errorf("hashing %s status: %v", imageMapName, err) 52 } 53 } 54 55 return w.done(), nil 56 } 57 58 type hashWriter struct { 59 h hash.Hash 60 } 61 62 func newHashWriter() *hashWriter { 63 return &hashWriter{h: crypto.SHA1.New()} 64 } 65 66 func (w hashWriter) append(o interface{}) error { 67 data, err := defaultJSONIterator.Marshal(o) 68 if err != nil { 69 return errors.Wrap(err, "serializing object for hash") 70 } 71 _, err = w.h.Write(data) 72 if err != nil { 73 return errors.Wrap(err, "computing hash") 74 } 75 return nil 76 } 77 78 func (w hashWriter) done() string { 79 return base64.URLEncoding.EncodeToString(w.h.Sum(nil)) 80 }