Skip to content

Commit 2166b58

Browse files
committed
Verify artifacts integrity
After downloading an artifact, compute its checksum and verify that it matches the original checksum advertised by source-controller. Signed-off-by: Stefan Prodan <stefan.prodan@gmail.com>
1 parent 9e51c3a commit 2166b58

File tree

1 file changed

+33
-1
lines changed

1 file changed

+33
-1
lines changed

controllers/helmrelease_controller_chart.go

+33-1
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,10 @@ limitations under the License.
1717
package controllers
1818

1919
import (
20+
"bytes"
2021
"context"
22+
"crypto/sha1"
23+
"crypto/sha256"
2124
"fmt"
2225
"io"
2326
"io/ioutil"
@@ -126,13 +129,42 @@ func (r *HelmReleaseReconciler) loadHelmChart(source *sourcev1.HelmChart) (*char
126129
return nil, fmt.Errorf("artifact '%s' download failed (status code: %s)", source.GetArtifact().URL, resp.Status)
127130
}
128131

129-
if _, err = io.Copy(f, resp.Body); err != nil {
132+
var buf bytes.Buffer
133+
134+
// verify checksum matches origin
135+
if err := r.verifyArtifact(source.GetArtifact(), &buf, resp.Body); err != nil {
136+
return nil, err
137+
}
138+
139+
if _, err = io.Copy(f, &buf); err != nil {
130140
return nil, err
131141
}
132142

133143
return loader.Load(f.Name())
134144
}
135145

146+
func (r *HelmReleaseReconciler) verifyArtifact(artifact *sourcev1.Artifact, buf *bytes.Buffer, reader io.Reader) error {
147+
hasher := sha256.New()
148+
149+
// for backwards compatibility with source-controller v0.17.2 and older
150+
if len(artifact.Checksum) == 40 {
151+
hasher = sha1.New()
152+
}
153+
154+
// compute checksum
155+
mw := io.MultiWriter(hasher, buf)
156+
if _, err := io.Copy(mw, reader); err != nil {
157+
return err
158+
}
159+
160+
if checksum := fmt.Sprintf("%x", hasher.Sum(nil)); checksum != artifact.Checksum {
161+
return fmt.Errorf("failed to verify artifact: computed checksum '%s' doesn't match advertised '%s'",
162+
checksum, artifact.Checksum)
163+
}
164+
165+
return nil
166+
}
167+
136168
// deleteHelmChart deletes the v1beta1.HelmChart of the v2beta1.HelmRelease.
137169
func (r *HelmReleaseReconciler) deleteHelmChart(ctx context.Context, hr *v2.HelmRelease) error {
138170
if hr.Status.HelmChart == "" {

0 commit comments

Comments
 (0)