diff --git a/cmd/buildctl/build.go b/cmd/buildctl/build.go index 716ab1f3..003d6186 100644 --- a/cmd/buildctl/build.go +++ b/cmd/buildctl/build.go @@ -18,6 +18,7 @@ import ( "github.com/moby/buildkit/solver/errdefs" "github.com/moby/buildkit/solver/pb" "github.com/moby/buildkit/util/progress/progressui" + "github.com/moby/buildkit/util/stack" "github.com/opencontainers/go-digest" "github.com/pkg/errors" "github.com/sirupsen/logrus" @@ -298,7 +299,7 @@ func buildAction(clicontext *cli.Context) error { // temp test if os.Getenv("BUILDCTL_DEBUG_ERROR_UNSTABLE") == "1" { - log.Printf("%+v", errdefs.StackFormatter(err)) + log.Printf("%+v", stack.Formatter(err)) var ve *errdefs.VertexError if errors.As(err, &ve) { diff --git a/cmd/buildctl/main.go b/cmd/buildctl/main.go index bd6b9ac5..aaaf694c 100644 --- a/cmd/buildctl/main.go +++ b/cmd/buildctl/main.go @@ -7,10 +7,10 @@ import ( _ "github.com/moby/buildkit/client/connhelper/dockercontainer" _ "github.com/moby/buildkit/client/connhelper/kubepod" bccommon "github.com/moby/buildkit/cmd/buildctl/common" - "github.com/moby/buildkit/solver/errdefs" "github.com/moby/buildkit/util/apicaps" "github.com/moby/buildkit/util/appdefaults" "github.com/moby/buildkit/util/profiler" + "github.com/moby/buildkit/util/stack" "github.com/moby/buildkit/version" "github.com/sirupsen/logrus" "github.com/urfave/cli" @@ -19,7 +19,7 @@ import ( func init() { apicaps.ExportedProduct = "buildkit" - errdefs.SetVersionInfo(version.Version, version.Revision) + stack.SetVersionInfo(version.Version, version.Revision) } func main() { diff --git a/cmd/buildkitd/main.go b/cmd/buildkitd/main.go index 7d6fa4ef..0d28d24a 100644 --- a/cmd/buildkitd/main.go +++ b/cmd/buildkitd/main.go @@ -40,7 +40,6 @@ import ( "github.com/moby/buildkit/frontend/gateway/forwarder" "github.com/moby/buildkit/session" "github.com/moby/buildkit/solver/bboltcachestorage" - "github.com/moby/buildkit/solver/errdefs" "github.com/moby/buildkit/util/apicaps" "github.com/moby/buildkit/util/appcontext" "github.com/moby/buildkit/util/appdefaults" @@ -48,6 +47,7 @@ import ( "github.com/moby/buildkit/util/grpcerrors" "github.com/moby/buildkit/util/profiler" "github.com/moby/buildkit/util/resolver" + "github.com/moby/buildkit/util/stack" "github.com/moby/buildkit/version" "github.com/moby/buildkit/worker" specs "github.com/opencontainers/image-spec/specs-go/v1" @@ -61,7 +61,7 @@ import ( func init() { apicaps.ExportedProduct = "buildkit" - errdefs.SetVersionInfo(version.Version, version.Revision) + stack.SetVersionInfo(version.Version, version.Revision) seed.WithTimeAndRand() reexec.Init() diff --git a/executor/runcexecutor/executor.go b/executor/runcexecutor/executor.go index 26e432e6..dc16c8f0 100644 --- a/executor/runcexecutor/executor.go +++ b/executor/runcexecutor/executor.go @@ -23,6 +23,7 @@ import ( "github.com/moby/buildkit/solver/pb" "github.com/moby/buildkit/util/network" rootlessspecconv "github.com/moby/buildkit/util/rootless/specconv" + "github.com/moby/buildkit/util/stack" "github.com/pkg/errors" "github.com/sirupsen/logrus" ) @@ -302,7 +303,7 @@ func (w *runcExecutor) Exec(ctx context.Context, meta executor.Meta, root cache. case <-ctx.Done(): return errors.Wrapf(ctx.Err(), err.Error()) default: - return err + return stack.Enable(err) } } diff --git a/frontend/dockerfile/cmd/dockerfile-frontend/main.go b/frontend/dockerfile/cmd/dockerfile-frontend/main.go index 641f6b2f..4e2dc6dd 100644 --- a/frontend/dockerfile/cmd/dockerfile-frontend/main.go +++ b/frontend/dockerfile/cmd/dockerfile-frontend/main.go @@ -7,13 +7,13 @@ import ( dockerfile "github.com/moby/buildkit/frontend/dockerfile/builder" "github.com/moby/buildkit/frontend/gateway/grpcclient" - "github.com/moby/buildkit/solver/errdefs" "github.com/moby/buildkit/util/appcontext" + "github.com/moby/buildkit/util/stack" "github.com/sirupsen/logrus" ) func init() { - errdefs.SetVersionInfo(Version, Revision) + stack.SetVersionInfo(Version, Revision) } func main() { diff --git a/frontend/dockerfile/parser/errors.go b/frontend/dockerfile/parser/errors.go index 206448b9..9f28a5a2 100644 --- a/frontend/dockerfile/parser/errors.go +++ b/frontend/dockerfile/parser/errors.go @@ -1,6 +1,9 @@ package parser -import "github.com/pkg/errors" +import ( + "github.com/moby/buildkit/util/stack" + "github.com/pkg/errors" +) // ErrorLocation gives a location in source code that caused the error type ErrorLocation struct { @@ -38,14 +41,10 @@ func WithLocation(err error, location []Range) error { if errors.As(err, &el) { return err } - var err1 error = &ErrorLocation{ + return stack.Enable(&ErrorLocation{ error: err, Location: location, - } - if !hasLocalStackTrace(err) { - err1 = errors.WithStack(err1) - } - return err1 + }) } func toRanges(start, end int) (r []Range) { @@ -57,17 +56,3 @@ func toRanges(start, end int) (r []Range) { } return } - -func hasLocalStackTrace(err error) bool { - wrapped, ok := err.(interface { - Unwrap() error - }) - if ok && hasLocalStackTrace(wrapped.Unwrap()) { - return true - } - - _, ok = err.(interface { - StackTrace() errors.StackTrace - }) - return ok -} diff --git a/frontend/gateway/gateway.go b/frontend/gateway/gateway.go index ed9b3ce0..f70fdbaa 100644 --- a/frontend/gateway/gateway.go +++ b/frontend/gateway/gateway.go @@ -27,7 +27,6 @@ import ( "github.com/moby/buildkit/identity" "github.com/moby/buildkit/session" "github.com/moby/buildkit/solver" - "github.com/moby/buildkit/solver/errdefs" opspb "github.com/moby/buildkit/solver/pb" "github.com/moby/buildkit/util/apicaps" "github.com/moby/buildkit/util/grpcerrors" @@ -674,7 +673,7 @@ func (lbf *llbBridgeForwarder) Ping(context.Context, *pb.PingRequest) (*pb.PongR func (lbf *llbBridgeForwarder) Return(ctx context.Context, in *pb.ReturnRequest) (*pb.ReturnResponse, error) { if in.Error != nil { - return lbf.setResult(nil, errdefs.FromGRPC(status.ErrorProto(&spb.Status{ + return lbf.setResult(nil, grpcerrors.FromGRPC(status.ErrorProto(&spb.Status{ Code: in.Error.Code, Message: in.Error.Message, Details: convertGogoAny(in.Error.Details), diff --git a/frontend/gateway/grpcclient/client.go b/frontend/gateway/grpcclient/client.go index baf02d32..9e73cdc3 100644 --- a/frontend/gateway/grpcclient/client.go +++ b/frontend/gateway/grpcclient/client.go @@ -15,7 +15,6 @@ import ( "github.com/moby/buildkit/client/llb" "github.com/moby/buildkit/frontend/gateway/client" pb "github.com/moby/buildkit/frontend/gateway/pb" - "github.com/moby/buildkit/solver/errdefs" opspb "github.com/moby/buildkit/solver/pb" "github.com/moby/buildkit/util/apicaps" "github.com/moby/buildkit/util/grpcerrors" @@ -154,7 +153,7 @@ func (c *grpcClient) Run(ctx context.Context, f client.BuildFunc) (retError erro } } if retError != nil { - st, _ := status.FromError(errdefs.ToGRPC(retError)) + st, _ := status.FromError(grpcerrors.ToGRPC(retError)) stp := st.Proto() req.Error = &rpc.Status{ Code: stp.Code, diff --git a/solver/errdefs/errdefs.pb.go b/solver/errdefs/errdefs.pb.go index f62251d9..abe03830 100644 --- a/solver/errdefs/errdefs.pb.go +++ b/solver/errdefs/errdefs.pb.go @@ -20,132 +20,6 @@ var _ = math.Inf // proto package needs to be updated. const _ = proto.ProtoPackageIsVersion3 // please upgrade the proto package -type Stack struct { - Frames []*Frame `protobuf:"bytes,1,rep,name=frames,proto3" json:"frames,omitempty"` - Cmdline []string `protobuf:"bytes,2,rep,name=cmdline,proto3" json:"cmdline,omitempty"` - Pid int32 `protobuf:"varint,3,opt,name=pid,proto3" json:"pid,omitempty"` - Version string `protobuf:"bytes,4,opt,name=version,proto3" json:"version,omitempty"` - Revision string `protobuf:"bytes,5,opt,name=revision,proto3" json:"revision,omitempty"` - XXX_NoUnkeyedLiteral struct{} `json:"-"` - XXX_unrecognized []byte `json:"-"` - XXX_sizecache int32 `json:"-"` -} - -func (m *Stack) Reset() { *m = Stack{} } -func (m *Stack) String() string { return proto.CompactTextString(m) } -func (*Stack) ProtoMessage() {} -func (*Stack) Descriptor() ([]byte, []int) { - return fileDescriptor_689dc58a5060aff5, []int{0} -} - -func (m *Stack) XXX_Unmarshal(b []byte) error { - return xxx_messageInfo_Stack.Unmarshal(m, b) -} -func (m *Stack) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { - return xxx_messageInfo_Stack.Marshal(b, m, deterministic) -} -func (m *Stack) XXX_Merge(src proto.Message) { - xxx_messageInfo_Stack.Merge(m, src) -} -func (m *Stack) XXX_Size() int { - return xxx_messageInfo_Stack.Size(m) -} -func (m *Stack) XXX_DiscardUnknown() { - xxx_messageInfo_Stack.DiscardUnknown(m) -} - -var xxx_messageInfo_Stack proto.InternalMessageInfo - -func (m *Stack) GetFrames() []*Frame { - if m != nil { - return m.Frames - } - return nil -} - -func (m *Stack) GetCmdline() []string { - if m != nil { - return m.Cmdline - } - return nil -} - -func (m *Stack) GetPid() int32 { - if m != nil { - return m.Pid - } - return 0 -} - -func (m *Stack) GetVersion() string { - if m != nil { - return m.Version - } - return "" -} - -func (m *Stack) GetRevision() string { - if m != nil { - return m.Revision - } - return "" -} - -type Frame struct { - Name string `protobuf:"bytes,1,opt,name=Name,proto3" json:"Name,omitempty"` - File string `protobuf:"bytes,2,opt,name=File,proto3" json:"File,omitempty"` - Line int32 `protobuf:"varint,3,opt,name=Line,proto3" json:"Line,omitempty"` - XXX_NoUnkeyedLiteral struct{} `json:"-"` - XXX_unrecognized []byte `json:"-"` - XXX_sizecache int32 `json:"-"` -} - -func (m *Frame) Reset() { *m = Frame{} } -func (m *Frame) String() string { return proto.CompactTextString(m) } -func (*Frame) ProtoMessage() {} -func (*Frame) Descriptor() ([]byte, []int) { - return fileDescriptor_689dc58a5060aff5, []int{1} -} - -func (m *Frame) XXX_Unmarshal(b []byte) error { - return xxx_messageInfo_Frame.Unmarshal(m, b) -} -func (m *Frame) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { - return xxx_messageInfo_Frame.Marshal(b, m, deterministic) -} -func (m *Frame) XXX_Merge(src proto.Message) { - xxx_messageInfo_Frame.Merge(m, src) -} -func (m *Frame) XXX_Size() int { - return xxx_messageInfo_Frame.Size(m) -} -func (m *Frame) XXX_DiscardUnknown() { - xxx_messageInfo_Frame.DiscardUnknown(m) -} - -var xxx_messageInfo_Frame proto.InternalMessageInfo - -func (m *Frame) GetName() string { - if m != nil { - return m.Name - } - return "" -} - -func (m *Frame) GetFile() string { - if m != nil { - return m.File - } - return "" -} - -func (m *Frame) GetLine() int32 { - if m != nil { - return m.Line - } - return 0 -} - type Vertex struct { Digest string `protobuf:"bytes,1,opt,name=digest,proto3" json:"digest,omitempty"` XXX_NoUnkeyedLiteral struct{} `json:"-"` @@ -157,7 +31,7 @@ func (m *Vertex) Reset() { *m = Vertex{} } func (m *Vertex) String() string { return proto.CompactTextString(m) } func (*Vertex) ProtoMessage() {} func (*Vertex) Descriptor() ([]byte, []int) { - return fileDescriptor_689dc58a5060aff5, []int{2} + return fileDescriptor_689dc58a5060aff5, []int{0} } func (m *Vertex) XXX_Unmarshal(b []byte) error { @@ -199,7 +73,7 @@ func (m *Source) Reset() { *m = Source{} } func (m *Source) String() string { return proto.CompactTextString(m) } func (*Source) ProtoMessage() {} func (*Source) Descriptor() ([]byte, []int) { - return fileDescriptor_689dc58a5060aff5, []int{3} + return fileDescriptor_689dc58a5060aff5, []int{1} } func (m *Source) XXX_Unmarshal(b []byte) error { @@ -260,7 +134,7 @@ func (m *Range) Reset() { *m = Range{} } func (m *Range) String() string { return proto.CompactTextString(m) } func (*Range) ProtoMessage() {} func (*Range) Descriptor() ([]byte, []int) { - return fileDescriptor_689dc58a5060aff5, []int{4} + return fileDescriptor_689dc58a5060aff5, []int{2} } func (m *Range) XXX_Unmarshal(b []byte) error { @@ -307,7 +181,7 @@ func (m *Position) Reset() { *m = Position{} } func (m *Position) String() string { return proto.CompactTextString(m) } func (*Position) ProtoMessage() {} func (*Position) Descriptor() ([]byte, []int) { - return fileDescriptor_689dc58a5060aff5, []int{5} + return fileDescriptor_689dc58a5060aff5, []int{3} } func (m *Position) XXX_Unmarshal(b []byte) error { @@ -343,8 +217,6 @@ func (m *Position) GetCharacter() int32 { } func init() { - proto.RegisterType((*Stack)(nil), "errdefs.Stack") - proto.RegisterType((*Frame)(nil), "errdefs.Frame") proto.RegisterType((*Vertex)(nil), "errdefs.Vertex") proto.RegisterType((*Source)(nil), "errdefs.Source") proto.RegisterType((*Range)(nil), "errdefs.Range") @@ -354,26 +226,20 @@ func init() { func init() { proto.RegisterFile("errdefs.proto", fileDescriptor_689dc58a5060aff5) } var fileDescriptor_689dc58a5060aff5 = []byte{ - // 330 bytes of a gzipped FileDescriptorProto - 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x6c, 0x52, 0x4f, 0x4b, 0xfb, 0x40, - 0x10, 0x25, 0xbf, 0x74, 0xd3, 0x66, 0xfa, 0x53, 0x74, 0x10, 0x09, 0xe2, 0x21, 0x44, 0xd0, 0x1e, - 0xa4, 0x87, 0x7a, 0xf5, 0x56, 0xe8, 0x49, 0x44, 0xb6, 0xe8, 0x7d, 0x4d, 0xa6, 0x75, 0x31, 0x4d, - 0xca, 0x66, 0x2d, 0x1e, 0xfc, 0x12, 0x7e, 0x63, 0x99, 0x49, 0x9a, 0x1e, 0xf4, 0x36, 0xef, 0x4f, - 0xe6, 0xbd, 0x0c, 0x0b, 0x47, 0xe4, 0x5c, 0x41, 0xab, 0x66, 0xba, 0x75, 0xb5, 0xaf, 0x71, 0xd8, - 0xc1, 0xec, 0x3b, 0x00, 0xb5, 0xf4, 0x26, 0x7f, 0xc7, 0x6b, 0x88, 0x56, 0xce, 0x6c, 0xa8, 0x49, - 0x82, 0x34, 0x9c, 0x8c, 0x67, 0xc7, 0xd3, 0xfd, 0x27, 0x0b, 0xa6, 0x75, 0xa7, 0x62, 0x02, 0xc3, - 0x7c, 0x53, 0x94, 0xb6, 0xa2, 0xe4, 0x5f, 0x1a, 0x4e, 0x62, 0xbd, 0x87, 0x78, 0x02, 0xe1, 0xd6, - 0x16, 0x49, 0x98, 0x06, 0x13, 0xa5, 0x79, 0x64, 0xef, 0x8e, 0x5c, 0x63, 0xeb, 0x2a, 0x19, 0xa4, - 0x01, 0x7b, 0x3b, 0x88, 0x17, 0x30, 0x72, 0xb4, 0xb3, 0x22, 0x29, 0x91, 0x7a, 0x9c, 0xcd, 0x41, - 0x49, 0x24, 0x22, 0x0c, 0x1e, 0xcd, 0x86, 0x92, 0x40, 0x0c, 0x32, 0x33, 0xb7, 0xb0, 0x25, 0x67, - 0x0b, 0xc7, 0x33, 0x73, 0x0f, 0xdc, 0xa7, 0x4d, 0x96, 0x39, 0x4b, 0x21, 0x7a, 0x21, 0xe7, 0xe9, - 0x13, 0xcf, 0x21, 0x2a, 0xec, 0x9a, 0x1a, 0xdf, 0xed, 0xe9, 0x50, 0xf6, 0x05, 0xd1, 0xb2, 0xfe, - 0x70, 0x39, 0xe1, 0x2d, 0xc4, 0x65, 0x9d, 0x1b, 0x6f, 0xeb, 0xea, 0xf7, 0xdf, 0x6b, 0x53, 0xad, - 0x49, 0x1f, 0x0c, 0x5c, 0x7d, 0x65, 0x4b, 0xaa, 0xb8, 0x59, 0xdb, 0xa2, 0xc7, 0x78, 0x06, 0x8a, - 0x8d, 0xa5, 0x54, 0x89, 0x75, 0x0b, 0xb8, 0x5f, 0x61, 0xbc, 0x91, 0x1b, 0xfc, 0xd7, 0x32, 0x67, - 0xcf, 0xa0, 0x64, 0x33, 0xde, 0x80, 0x6a, 0xbc, 0x71, 0x6d, 0xbb, 0xf1, 0xec, 0xb4, 0x0f, 0x7e, - 0xaa, 0x1b, 0xcb, 0x89, 0xba, 0xd5, 0xf1, 0x0a, 0x42, 0xaa, 0x0a, 0x89, 0xfc, 0xd3, 0xc6, 0x6a, - 0x76, 0x0f, 0xa3, 0x3d, 0xd1, 0x9f, 0x25, 0x38, 0x9c, 0x05, 0x2f, 0x21, 0x9e, 0xbf, 0x19, 0x67, - 0x72, 0x4f, 0x4e, 0x56, 0x29, 0x7d, 0x20, 0x5e, 0x23, 0x79, 0x1d, 0x77, 0x3f, 0x01, 0x00, 0x00, - 0xff, 0xff, 0x52, 0xed, 0x4a, 0x2a, 0x2e, 0x02, 0x00, 0x00, + // 237 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x6c, 0x90, 0xbb, 0x4b, 0x04, 0x31, + 0x10, 0xc6, 0x59, 0xf7, 0xb2, 0xde, 0xce, 0xa9, 0xe0, 0x20, 0x12, 0xc4, 0x62, 0x59, 0x0b, 0xb7, + 0x90, 0x2b, 0xce, 0xd6, 0xce, 0xd6, 0x42, 0x22, 0xda, 0xc7, 0xdd, 0xb9, 0x33, 0xb0, 0x26, 0x32, + 0x89, 0x60, 0xe1, 0x1f, 0x2f, 0x99, 0xbd, 0x47, 0x63, 0x37, 0xdf, 0x83, 0xdf, 0x17, 0x02, 0xa7, + 0xc4, 0x3c, 0xd0, 0x3a, 0x2e, 0xbf, 0x38, 0xa4, 0x80, 0xc7, 0x5b, 0xd9, 0x36, 0x50, 0xbd, 0x11, + 0x27, 0xfa, 0xc1, 0x4b, 0xa8, 0x06, 0xb7, 0xa1, 0x98, 0x74, 0xd1, 0x14, 0x5d, 0x6d, 0xb6, 0xaa, + 0xfd, 0x85, 0xea, 0x25, 0x7c, 0x73, 0x4f, 0x78, 0x07, 0xf5, 0x18, 0x7a, 0x9b, 0x5c, 0xf0, 0x51, + 0x17, 0x4d, 0xd9, 0x2d, 0x56, 0x67, 0xcb, 0x1d, 0xd7, 0x58, 0xbf, 0x21, 0x73, 0x28, 0xe0, 0x15, + 0xcc, 0xd7, 0x6e, 0x24, 0x6f, 0x3f, 0x49, 0x1f, 0x09, 0x71, 0xaf, 0xf1, 0x02, 0x54, 0x2e, 0x8e, + 0xba, 0x94, 0x60, 0x12, 0x88, 0x30, 0x1b, 0x6c, 0xb2, 0x7a, 0xd6, 0x14, 0xdd, 0x89, 0x91, 0xbb, + 0x7d, 0x05, 0x25, 0x64, 0xbc, 0x05, 0x15, 0x93, 0xe5, 0xe9, 0x75, 0x8b, 0xd5, 0xf9, 0x7e, 0xf8, + 0x39, 0x44, 0x97, 0x17, 0xcd, 0x94, 0xe3, 0x0d, 0x94, 0xe4, 0x07, 0x99, 0xfc, 0xb7, 0x96, 0xd3, + 0xf6, 0x01, 0xe6, 0x3b, 0x23, 0xcf, 0x3e, 0x39, 0x4f, 0x02, 0x56, 0x46, 0x6e, 0xbc, 0x86, 0xfa, + 0xf1, 0xc3, 0xb2, 0xed, 0x13, 0xb1, 0xa0, 0x94, 0x39, 0x18, 0xef, 0x95, 0x7c, 0xe2, 0xfd, 0x5f, + 0x00, 0x00, 0x00, 0xff, 0xff, 0x49, 0x7f, 0xe8, 0xa9, 0x55, 0x01, 0x00, 0x00, } diff --git a/solver/errdefs/errdefs.proto b/solver/errdefs/errdefs.proto index c4016222..951140c9 100644 --- a/solver/errdefs/errdefs.proto +++ b/solver/errdefs/errdefs.proto @@ -2,20 +2,6 @@ syntax = "proto3"; package errdefs; -message Stack { - repeated Frame frames = 1; - repeated string cmdline = 2; - int32 pid = 3; - string version = 4; - string revision = 5; -} - -message Frame { - string Name = 1; - string File = 2; - int32 Line = 3; -} - message Vertex { string digest = 1; } @@ -35,4 +21,4 @@ message Range { message Position { int32 Line = 1; int32 Character = 2; -} \ No newline at end of file +} diff --git a/solver/errdefs/grpc.go b/solver/errdefs/grpc.go deleted file mode 100644 index e6de6968..00000000 --- a/solver/errdefs/grpc.go +++ /dev/null @@ -1,156 +0,0 @@ -package errdefs - -import ( - "github.com/golang/protobuf/proto" - "github.com/golang/protobuf/ptypes" - "github.com/opencontainers/go-digest" - "github.com/pkg/errors" - spb "google.golang.org/genproto/googleapis/rpc/status" - "google.golang.org/grpc/codes" - "google.golang.org/grpc/status" -) - -func ToGRPC(err error) error { - if err == nil { - return nil - } - st, ok := AsGRPCStatus(err) - if !ok || st == nil { - st = status.New(Code(err), err.Error()) - } - if st.Code() != Code(err) { - pb := st.Proto() - pb.Code = int32(Code(err)) - st = status.FromProto(pb) - } - - var details []proto.Message - - for _, st := range Traces(err) { - details = append(details, st) - } - - for _, st := range Sources(err) { - details = append(details, st) - } - - var ve *VertexError - if errors.As(err, &ve) { - details = append(details, &ve.Vertex) - } - - if len(details) > 0 { - if st2, err := st.WithDetails(details...); err == nil { - st = st2 - } - } - - return st.Err() -} - -func Code(err error) codes.Code { - if se, ok := err.(interface { - Code() codes.Code - }); ok { - return se.Code() - } - - wrapped, ok := err.(interface { - Unwrap() error - }) - if ok { - return Code(wrapped.Unwrap()) - } - - return status.FromContextError(err).Code() -} - -func WrapCode(err error, code codes.Code) error { - return &withCode{error: err, code: code} -} - -func AsGRPCStatus(err error) (*status.Status, bool) { - if err == nil { - return nil, true - } - if se, ok := err.(interface { - GRPCStatus() *status.Status - }); ok { - return se.GRPCStatus(), true - } - - wrapped, ok := err.(interface { - Unwrap() error - }) - if ok { - return AsGRPCStatus(wrapped.Unwrap()) - } - - return nil, false -} - -func FromGRPC(err error) error { - if err == nil { - return nil - } - st, ok := status.FromError(err) - if !ok { - return err - } - - pb := st.Proto() - - n := &spb.Status{ - Code: pb.Code, - Message: pb.Message, - } - - details := make([]interface{}, 0, len(pb.Details)) - - // details that we don't understand are copied as proto - for _, d := range pb.Details { - detail := &ptypes.DynamicAny{} - if err := ptypes.UnmarshalAny(d, detail); err != nil { - n.Details = append(n.Details, d) - continue - } - switch detail.Message.(type) { - case *Stack, *Vertex, *Source: - details = append(details, detail.Message) - default: - n.Details = append(n.Details, d) - } - } - - err = status.FromProto(n).Err() - - for _, d := range details { - switch v := d.(type) { - case *Stack: - if v != nil { - err = &withStack{stack: *v, error: err} - } - case *Vertex: - err = WrapVertex(err, digest.Digest(v.Digest)) - case *Source: - if v != nil { - err = WithSource(err, *v) - } - } - } - - if !hasLocalStackTrace(err) { - err = errors.WithStack(err) - } - - return err -} - -type withCode struct { - code codes.Code - error -} - -func (e *withCode) Unwrap() error { - return e.error -} diff --git a/solver/errdefs/source.go b/solver/errdefs/source.go index be0cddbe..74284db5 100644 --- a/solver/errdefs/source.go +++ b/solver/errdefs/source.go @@ -1,6 +1,9 @@ package errdefs -import "github.com/pkg/errors" +import ( + "github.com/moby/buildkit/util/grpcerrors" + "github.com/pkg/errors" +) func WithSource(err error, src Source) error { if err == nil { @@ -18,6 +21,10 @@ func (e *ErrorSource) Unwrap() error { return e.error } +func (e *ErrorSource) ToProto() grpcerrors.TypedErrorProto { + return &e.Source +} + func Sources(err error) []*Source { var out []*Source var es *ErrorSource @@ -27,3 +34,7 @@ func Sources(err error) []*Source { } return out } + +func (s *Source) WrapError(err error) error { + return &ErrorSource{error: err, Source: *s} +} diff --git a/solver/errdefs/stack.go b/solver/errdefs/stack.go deleted file mode 100644 index d924a433..00000000 --- a/solver/errdefs/stack.go +++ /dev/null @@ -1,133 +0,0 @@ -package errdefs - -import ( - "fmt" - io "io" - "os" - "strconv" - "strings" - - "github.com/pkg/errors" -) - -var version string -var revision string - -func SetVersionInfo(v, r string) { - version = v - revision = r -} - -func Traces(err error) []*Stack { - var st []*Stack - - wrapped, ok := err.(interface { - Unwrap() error - }) - if ok { - st = Traces(wrapped.Unwrap()) - } - - if ste, ok := err.(interface { - StackTrace() errors.StackTrace - }); ok { - st = append(st, convertStack(ste.StackTrace())) - } - - if ste, ok := err.(interface { - StackTrace() *Stack - }); ok { - st = append(st, ste.StackTrace()) - } - - return st -} - -func hasLocalStackTrace(err error) bool { - wrapped, ok := err.(interface { - Unwrap() error - }) - if ok && hasLocalStackTrace(wrapped.Unwrap()) { - return true - } - - _, ok = err.(interface { - StackTrace() errors.StackTrace - }) - return ok -} - -func StackFormatter(err error) fmt.Formatter { - return &stackFormatter{err} -} - -type stackFormatter struct { - error -} - -func (w *stackFormatter) Format(s fmt.State, verb rune) { - switch verb { - case 'v': - if s.Flag('+') { - fmt.Fprintf(s, "%+v\n", w.Error()) - for _, stack := range Traces(w.error) { - fmt.Fprintf(s, "%d %s %s\n", stack.Pid, stack.Version, strings.Join(stack.Cmdline, " ")) - for _, f := range stack.Frames { - fmt.Fprintf(s, "%s\n\t%s:%d\n", f.Name, f.File, f.Line) - } - fmt.Fprintf(s, "\n") - } - return - } - fallthrough - case 's': - io.WriteString(s, w.Error()) - case 'q': - fmt.Fprintf(s, "%q", w.Error()) - } -} - -func convertStack(s errors.StackTrace) *Stack { - var out Stack - for _, f := range s { - dt, err := f.MarshalText() - if err != nil { - continue - } - p := strings.SplitN(string(dt), " ", 2) - if len(p) != 2 { - continue - } - idx := strings.LastIndexByte(p[1], ':') - if idx == -1 { - continue - } - line, err := strconv.Atoi(p[1][idx+1:]) - if err != nil { - continue - } - out.Frames = append(out.Frames, &Frame{ - Name: p[0], - File: p[1][:idx], - Line: int32(line), - }) - } - out.Cmdline = os.Args - out.Pid = int32(os.Getpid()) - out.Version = version - out.Revision = revision - return &out -} - -type withStack struct { - stack Stack - error -} - -func (e *withStack) Unwrap() error { - return e.error -} - -func (e *withStack) StackTrace() *Stack { - return &e.stack -} diff --git a/solver/errdefs/vertex.go b/solver/errdefs/vertex.go index eb06a018..adc5e378 100644 --- a/solver/errdefs/vertex.go +++ b/solver/errdefs/vertex.go @@ -1,6 +1,9 @@ package errdefs -import "github.com/opencontainers/go-digest" +import ( + "github.com/moby/buildkit/util/grpcerrors" + "github.com/opencontainers/go-digest" +) type VertexError struct { Vertex @@ -11,9 +14,17 @@ func (e *VertexError) Unwrap() error { return e.error } +func (e *VertexError) ToProto() grpcerrors.TypedErrorProto { + return &e.Vertex +} + func WrapVertex(err error, dgst digest.Digest) error { if err == nil { return nil } return &VertexError{Vertex: Vertex{Digest: dgst.String()}, error: err} } + +func (v *Vertex) WrapError(err error) error { + return &VertexError{error: err, Vertex: *v} +} diff --git a/util/grpcerrors/grpcerrors.go b/util/grpcerrors/grpcerrors.go index bf285756..cecc68c3 100644 --- a/util/grpcerrors/grpcerrors.go +++ b/util/grpcerrors/grpcerrors.go @@ -60,6 +60,12 @@ func Code(err error) codes.Code { return se.Code() } + if se, ok := err.(interface { + GRPCStatus() *status.Status + }); ok { + return se.GRPCStatus().Code() + } + wrapped, ok := err.(interface { Unwrap() error }) diff --git a/util/stack/stack.go b/util/stack/stack.go index 9b6f6950..6d3cfc83 100644 --- a/util/stack/stack.go +++ b/util/stack/stack.go @@ -71,25 +71,29 @@ func hasLocalStackTrace(err error) bool { return ok } -func StackFormatter(err error) fmt.Formatter { - return &stackFormatter{err} +func Formatter(err error) fmt.Formatter { + return &formatter{err} } -type stackFormatter struct { +type formatter struct { error } -func (w *stackFormatter) Format(s fmt.State, verb rune) { +func (w *formatter) Format(s fmt.State, verb rune) { + if w.error == nil { + fmt.Fprintf(s, "%v", w.error) + return + } switch verb { case 'v': if s.Flag('+') { - fmt.Fprintf(s, "%+v\n", w.Error()) + fmt.Fprintf(s, "%s\n", w.Error()) for _, stack := range Traces(w.error) { fmt.Fprintf(s, "%d %s %s\n", stack.Pid, stack.Version, strings.Join(stack.Cmdline, " ")) for _, f := range stack.Frames { fmt.Fprintf(s, "%s\n\t%s:%d\n", f.Name, f.File, f.Line) } - fmt.Fprintf(s, "\n") + fmt.Fprintln(s) } return }