mirror of
https://github.com/moby/buildkit.git
synced 2026-08-04 14:50:21 +00:00
91 lines
2.3 KiB
Go
91 lines
2.3 KiB
Go
package proc
|
|
|
|
import (
|
|
"context"
|
|
|
|
"github.com/moby/buildkit/client/llb"
|
|
"github.com/moby/buildkit/client/llb/sourceresolver"
|
|
"github.com/moby/buildkit/executor/resources"
|
|
"github.com/moby/buildkit/exporter/containerimage/exptypes"
|
|
"github.com/moby/buildkit/frontend"
|
|
"github.com/moby/buildkit/frontend/attestations/sbom"
|
|
"github.com/moby/buildkit/solver"
|
|
"github.com/moby/buildkit/solver/llbsolver"
|
|
"github.com/moby/buildkit/solver/result"
|
|
"github.com/moby/buildkit/util/tracing"
|
|
"github.com/pkg/errors"
|
|
)
|
|
|
|
func SBOMProcessor(scannerRef string, useCache bool, resolveMode string, params map[string]string) llbsolver.Processor {
|
|
return func(ctx context.Context, res *llbsolver.Result, s *llbsolver.Solver, j *solver.Job, usage *resources.SysSampler) (*llbsolver.Result, error) {
|
|
// skip sbom generation if we already have an sbom
|
|
if sbom.HasSBOM(res.Result) {
|
|
return res, nil
|
|
}
|
|
|
|
span, ctx := tracing.StartSpan(ctx, "create sbom attestation")
|
|
defer span.End()
|
|
|
|
ps, err := exptypes.ParsePlatforms(res.Metadata)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
|
|
scanner, err := sbom.CreateSBOMScanner(ctx, s.Bridge(j), scannerRef, sourceresolver.Opt{
|
|
ImageOpt: &sourceresolver.ResolveImageOpt{
|
|
ResolveMode: resolveMode,
|
|
},
|
|
}, params)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
if scanner == nil {
|
|
return res, nil
|
|
}
|
|
|
|
for _, p := range ps.Platforms {
|
|
ref, ok := res.FindRef(p.ID)
|
|
if !ok {
|
|
return nil, errors.Errorf("could not find ref %s", p.ID)
|
|
}
|
|
if ref == nil {
|
|
continue
|
|
}
|
|
|
|
defop, err := llb.NewDefinitionOp(ref.Definition())
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
st := llb.NewState(defop)
|
|
|
|
var opts []llb.ConstraintsOpt
|
|
if !useCache {
|
|
opts = append(opts, llb.IgnoreCache)
|
|
}
|
|
att, err := scanner(ctx, p.ID, st, nil, opts...)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
attSolve, err := result.ConvertAttestation(&att, func(st *llb.State) (solver.ResultProxy, error) {
|
|
def, err := st.Marshal(ctx)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
|
|
r, err := s.Bridge(j).Solve(ctx, frontend.SolveRequest{
|
|
Definition: def.ToPB(),
|
|
}, j.SessionID)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
return r.Ref, nil
|
|
})
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
res.AddAttestation(p.ID, *attSolve)
|
|
}
|
|
return res, nil
|
|
}
|
|
}
|