Skip to content

Commit 00a2fc8

Browse files
committed
debug: evaluate all refs to allow multi-platform debugging
Signed-off-by: Justin Chadwell <[email protected]>
1 parent cb061b6 commit 00a2fc8

File tree

1 file changed

+51
-34
lines changed

1 file changed

+51
-34
lines changed

build/result.go

Lines changed: 51 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -14,9 +14,11 @@ import (
1414
gateway "github.com/moby/buildkit/frontend/gateway/client"
1515
"github.com/moby/buildkit/solver/errdefs"
1616
"github.com/moby/buildkit/solver/pb"
17+
"github.com/moby/buildkit/solver/result"
1718
specs "github.com/opencontainers/image-spec/specs-go/v1"
1819
"github.com/pkg/errors"
1920
"github.com/sirupsen/logrus"
21+
"golang.org/x/sync/errgroup"
2022
)
2123

2224
func NewResultContext(ctx context.Context, c *client.Client, solveOpt client.SolveOpt, res *gateway.Result) (*ResultContext, error) {
@@ -27,23 +29,21 @@ func NewResultContext(ctx context.Context, c *client.Client, solveOpt client.Sol
2729
return getResultAt(ctx, c, solveOpt, def, nil)
2830
}
2931

30-
func getDefinition(ctx context.Context, res *gateway.Result) (*pb.Definition, error) {
31-
ref, err := res.SingleRef()
32-
if err != nil {
33-
return nil, err
34-
}
35-
st, err := ref.ToState()
36-
if err != nil {
37-
return nil, err
38-
}
39-
def, err := st.Marshal(ctx)
40-
if err != nil {
41-
return nil, err
42-
}
43-
return def.ToPB(), nil
32+
func getDefinition(ctx context.Context, res *gateway.Result) (*result.Result[*pb.Definition], error) {
33+
return result.ConvertResult(res, func(ref gateway.Reference) (*pb.Definition, error) {
34+
st, err := ref.ToState()
35+
if err != nil {
36+
return nil, err
37+
}
38+
def, err := st.Marshal(ctx)
39+
if err != nil {
40+
return nil, err
41+
}
42+
return def.ToPB(), nil
43+
})
4444
}
4545

46-
func getResultAt(ctx context.Context, c *client.Client, solveOpt client.SolveOpt, target *pb.Definition, statusChan chan *client.SolveStatus) (*ResultContext, error) {
46+
func getResultAt(ctx context.Context, c *client.Client, solveOpt client.SolveOpt, targets *result.Result[*pb.Definition], statusChan chan *client.SolveStatus) (*ResultContext, error) {
4747
ctx, cancel := context.WithCancel(ctx)
4848
defer cancel()
4949

@@ -77,19 +77,43 @@ func getResultAt(ctx context.Context, c *client.Client, solveOpt client.SolveOpt
7777
_, err := c.Build(context.Background(), solveOpt, "buildx", func(ctx context.Context, c gateway.Client) (*gateway.Result, error) {
7878
ctx, cancel := context.WithCancel(ctx)
7979
defer cancel()
80-
resultCtx := ResultContext{}
81-
res2, err := c.Solve(ctx, gateway.SolveRequest{
82-
Evaluate: true,
83-
Definition: target,
80+
81+
// force evaluation of all targets in parallel
82+
results := make(map[*pb.Definition]*gateway.Result)
83+
resultsMu := sync.Mutex{}
84+
eg, egCtx := errgroup.WithContext(ctx)
85+
targets.EachRef(func(def *pb.Definition) error {
86+
eg.Go(func() error {
87+
res2, err := c.Solve(egCtx, gateway.SolveRequest{
88+
Evaluate: true,
89+
Definition: def,
90+
})
91+
if err != nil {
92+
return err
93+
}
94+
resultsMu.Lock()
95+
results[def] = res2
96+
resultsMu.Unlock()
97+
return nil
98+
})
99+
return nil
84100
})
85-
if err != nil {
101+
resultCtx := ResultContext{}
102+
if err := eg.Wait(); err != nil {
86103
var se *errdefs.SolveError
87104
if errors.As(err, &se) {
88105
resultCtx.solveErr = se
89106
} else {
90107
return nil, err
91108
}
92109
}
110+
res2, _ := result.ConvertResult(targets, func(def *pb.Definition) (gateway.Reference, error) {
111+
if res, ok := results[def]; ok {
112+
return res.Ref, nil
113+
}
114+
return nil, nil
115+
})
116+
93117
// Record the client and ctx as well so that containers can be created from the SolveError.
94118
resultCtx.res = res2
95119
resultCtx.gwClient = c
@@ -192,32 +216,25 @@ func (r *ResultContext) getProcessConfig(cfg *controllerapi.InvokeConfig, stdin
192216
}
193217

194218
func containerConfigFromResult(ctx context.Context, res *gateway.Result, c gateway.Client, cfg controllerapi.InvokeConfig) (*gateway.NewContainerRequest, error) {
195-
if res.Ref == nil {
196-
return nil, errors.Errorf("no reference is registered")
197-
}
198219
if cfg.Initial {
199220
return nil, errors.Errorf("starting from the container from the initial state of the step is supported only on the failed steps")
200221
}
201-
st, err := res.Ref.ToState()
202-
if err != nil {
203-
return nil, err
204-
}
205-
def, err := st.Marshal(ctx)
222+
223+
ps, err := exptypes.ParsePlatforms(res.Metadata)
206224
if err != nil {
207225
return nil, err
208226
}
209-
imgRef, err := c.Solve(ctx, gateway.SolveRequest{
210-
Definition: def.ToPB(),
211-
})
212-
if err != nil {
213-
return nil, err
227+
ref, ok := res.FindRef(ps.Platforms[0].ID)
228+
if !ok {
229+
return nil, errors.Errorf("no reference found")
214230
}
231+
215232
return &gateway.NewContainerRequest{
216233
Mounts: []gateway.Mount{
217234
{
218235
Dest: "/",
219236
MountType: pb.MountType_BIND,
220-
Ref: imgRef.Ref,
237+
Ref: ref,
221238
},
222239
},
223240
}, nil

0 commit comments

Comments
 (0)