Skip to content

Commit

Permalink
Merge pull request #91 from logicfox/main
Browse files Browse the repository at this point in the history
[fix] handle copa error when there are no patchable vulnerabilities
  • Loading branch information
logicfox authored Aug 26, 2024
2 parents fb53792 + b2e626e commit 604a53c
Show file tree
Hide file tree
Showing 4 changed files with 36 additions and 20 deletions.
13 changes: 10 additions & 3 deletions internal/program.go
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,11 @@ var (
func Program(args []string) error {
ctx := context.TODO()

logger := slog.New(slog.NewJSONHandler(os.Stdout, nil))
slogHandlerOpts := &slog.HandlerOptions{}
if os.Getenv("HELMPER_LOG_LEVEL") == "DEBUG" {
slogHandlerOpts.Level = slog.LevelDebug
}
logger := slog.New(slog.NewJSONHandler(os.Stdout, slogHandlerOpts))
slog.SetDefault(logger)

output.Header(version, commit, date)
Expand Down Expand Up @@ -211,10 +215,11 @@ func Program(args []string) error {
ModifyRegistry: importConfig.Import.ReplaceRegistryReferences,
}.Run(ctx, opts...)
if err != nil {
return err
return fmt.Errorf("internal: error importing chart to registry: %w", err)
}

if importConfig.Import.Cosign.Enabled {
slog.Debug("Cosign enabled")
signo := mySign.SignChartOption{
ChartCollection: &charts,
Registries: registries,
Expand All @@ -225,14 +230,15 @@ func Program(args []string) error {
AllowHTTPRegistry: importConfig.Import.Cosign.AllowHTTPRegistry,
}
if err := signo.Run(); err != nil {
slog.Error("Error signing with Cosign")
return err
}
}
}

switch {
case importConfig.Import.Enabled && importConfig.Import.Copacetic.Enabled:

slog.Debug("Import enabled and Copacetic enabled")
patch := make([]*registry.Image, 0)
push := make([]*registry.Image, 0)

Expand Down Expand Up @@ -463,6 +469,7 @@ func Program(args []string) error {
}

case importConfig.Import.Enabled:
slog.Debug("Only import enabled")
// convert to pointer array to enable mutable values
imgPs := make([]*registry.Image, 0)
for _, i := range imgs {
Expand Down
2 changes: 1 addition & 1 deletion pkg/copa/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,7 @@ func (o PatchOption) Run(ctx context.Context, reportFilePaths map[*registry.Imag
CertPath: o.Buildkit.CertPath,
KeyPath: o.Buildkit.KeyPath,
}, outFilePaths[i]); err != nil {
return err
return fmt.Errorf("error patching image %s :: %w ", ref, err)
}

_ = bar.Add(1)
Expand Down
31 changes: 20 additions & 11 deletions pkg/copa/patch.go
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,10 @@ func Patch(ctx context.Context, timeout time.Duration, image, reportFile, patche

select {
case err := <-ch:
return err
if err == nil {
return nil
}
return fmt.Errorf("copa: error patching image :: %w", err)
case <-timeoutCtx.Done():
// add a grace period for long running deferred cleanup functions to complete
<-time.After(1 * time.Second)
Expand Down Expand Up @@ -131,14 +134,14 @@ func patchWithContext(ctx context.Context, ch chan error, image, reportFile, pat
if reportFile != "" {
updates, err = report.TryParseScanReport(reportFile, scanner)
if err != nil {
return err
return fmt.Errorf("copa: error parsing scan report %s :: %w", reportFile, err)
}
log.Debugf("updates to apply: %v", updates)
}

bkClient, err := buildkit.NewClient(ctx, bkOpts)
if err != nil {
return err
return fmt.Errorf("copa: error creating buildkit client :: %w", err)
}
defer bkClient.Close()

Expand All @@ -162,7 +165,7 @@ func patchWithContext(ctx context.Context, ch chan error, image, reportFile, pat
}
solveOpt.SourcePolicy, err = build.ReadSourcePolicy()
if err != nil {
return err
return fmt.Errorf("copa: error reading source policy :: %w", err)
}

buildChannel := make(chan *client.SolveStatus)
Expand All @@ -173,7 +176,7 @@ func patchWithContext(ctx context.Context, ch chan error, image, reportFile, pat
config, err := buildkit.InitializeBuildkitConfig(ctx, c, imageName.String())
if err != nil {
ch <- err
return nil, err
return nil, fmt.Errorf("copa: error initializing buildkit config for image %s :: %w", imageName.String(), err)
}

// Create package manager helper
Expand All @@ -189,20 +192,20 @@ func patchWithContext(ctx context.Context, ch chan error, image, reportFile, pat
osType, err := getOSType(ctx, fileBytes)
if err != nil {
ch <- err
return nil, err
return nil, fmt.Errorf("copa: error getting os type :: %w", err)
}

osVersion, err := getOSVersion(ctx, fileBytes)
if err != nil {
ch <- err
return nil, err
return nil, fmt.Errorf("copa: error getting os version :: %w", err)
}

// get package manager based on os family type
manager, err = pkgmgr.GetPackageManager(osType, osVersion, config, workingFolder)
if err != nil {
ch <- err
return nil, err
return nil, fmt.Errorf("copa: error getting package manager for ostype=%s, version=%s :: %w", osType, osVersion, err)
}
// do not specify updates, will update all
updates = nil
Expand All @@ -211,16 +214,22 @@ func patchWithContext(ctx context.Context, ch chan error, image, reportFile, pat
manager, err = pkgmgr.GetPackageManager(updates.Metadata.OS.Type, updates.Metadata.OS.Version, config, workingFolder)
if err != nil {
ch <- err
return nil, err
return nil, fmt.Errorf("copa: error getting package manager by family type: ostype=%s, osversion=%s :: %w", updates.Metadata.OS.Type, updates.Metadata.OS.Version, err)
}
}

// Export the patched image state to Docker
// TODO: Add support for other output modes as buildctl does.
log.Infof("Patching %d vulnerabilities", len(updates.Updates))
patchedImageState, errPkgs, err := manager.InstallUpdates(ctx, updates, ignoreError)
log.Infof("Error is: %v", err)
if err != nil {
ch <- err
return nil, err
// if there are no patchable vulnerabilities, return nil without error
if len(updates.Updates) != 0 {
ch <- err
return nil, fmt.Errorf("copa: error installing updates for %s to address %d vulnerabilities :: %w", image, len(updates.Updates), err)
}
return nil, nil
}

def, err := patchedImageState.Marshal(ctx)
Expand Down
10 changes: 5 additions & 5 deletions pkg/helm/chartImportOption.go
Original file line number Diff line number Diff line change
Expand Up @@ -114,7 +114,7 @@ func (opt ChartImportOption) Run(ctx context.Context, setters ...Option) error {
}

for _, r := range opt.Registries {

registryURL := "oci://" + r.URL + "/charts"
if !opt.All {
_, err := r.Exist(ctx, "charts/"+c.Name, c.Version)
if err == nil {
Expand All @@ -125,18 +125,18 @@ func (opt ChartImportOption) Run(ctx context.Context, setters ...Option) error {
}

if opt.ModifyRegistry {
res, err := c.PushAndModify("oci://"+r.URL+"/charts", r.Insecure, r.PlainHTTP)
res, err := c.PushAndModify(registryURL, r.Insecure, r.PlainHTTP)
if err != nil {
return err
return fmt.Errorf("helm: error pushing and modifying chart %s to registry %s :: %w", c.Name, registryURL, err)
}
slog.Debug(res)

continue
}

res, err := c.Push("oci://"+r.URL+"/charts", r.Insecure, r.PlainHTTP)
res, err := c.Push(registryURL, r.Insecure, r.PlainHTTP)
if err != nil {
return err
return fmt.Errorf("helm: error pushing chart %s to registry %s :: %w", c.Name, registryURL, err)
}
slog.Debug(res)

Expand Down

0 comments on commit 604a53c

Please sign in to comment.