github.com/matrixorigin/matrixone@v0.7.0/pkg/util/trace/impl/motrace/report_error.go (about) 1 // Copyright 2022 Matrix Origin 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package motrace 16 17 import ( 18 "context" 19 "errors" 20 "fmt" 21 "sync/atomic" 22 "time" 23 "unsafe" 24 25 "github.com/cockroachdb/errors/errbase" 26 "github.com/matrixorigin/matrixone/pkg/common/moerr" 27 "github.com/matrixorigin/matrixone/pkg/logutil" 28 "github.com/matrixorigin/matrixone/pkg/util/errutil" 29 "github.com/matrixorigin/matrixone/pkg/util/export/table" 30 "github.com/matrixorigin/matrixone/pkg/util/trace" 31 "go.uber.org/zap" 32 ) 33 34 // MOErrorHolder implement export.IBuffer2SqlItem and export.CsvFields 35 type MOErrorHolder struct { 36 Error error `json:"error"` 37 Timestamp time.Time `json:"timestamp"` 38 } 39 40 func (h *MOErrorHolder) GetName() string { 41 return errorView.OriginTable.GetName() 42 } 43 44 func (h *MOErrorHolder) Size() int64 { 45 return int64(32*8) + int64(unsafe.Sizeof(h)) 46 } 47 func (h *MOErrorHolder) Free() { 48 h.Error = nil 49 } 50 51 func (h *MOErrorHolder) GetTable() *table.Table { return errorView.OriginTable } 52 53 func (h *MOErrorHolder) FillRow(ctx context.Context, row *table.Row) { 54 row.Reset() 55 row.SetColumnVal(rawItemCol, errorView.Table) 56 row.SetColumnVal(timestampCol, h.Timestamp) 57 row.SetColumnVal(nodeUUIDCol, GetNodeResource().NodeUuid) 58 row.SetColumnVal(nodeTypeCol, GetNodeResource().NodeType) 59 row.SetColumnVal(errorCol, h.Error.Error()) 60 row.SetColumnVal(stackCol, fmt.Sprintf(errorFormatter.Load().(string), h.Error)) 61 var moError *moerr.Error 62 if errors.As(h.Error, &moError) { 63 row.SetColumnVal(errCodeCol, fmt.Sprintf("%d", moError.ErrorCode())) 64 } 65 if ct := errutil.GetContextTracer(h.Error); ct != nil && ct.Context() != nil { 66 span := trace.SpanFromContext(ct.Context()) 67 row.SetColumnVal(traceIDCol, span.SpanContext().TraceID.String()) 68 row.SetColumnVal(spanIDCol, span.SpanContext().SpanID.String()) 69 row.SetColumnVal(spanKindCol, span.SpanContext().Kind.String()) 70 } 71 } 72 73 func (h *MOErrorHolder) Format(s fmt.State, verb rune) { errbase.FormatError(h.Error, s, verb) } 74 75 var disableLogErrorReport atomic.Bool 76 77 func DisableLogErrorReport(disable bool) { 78 disableLogErrorReport.Store(disable) 79 } 80 81 // ReportError send to BatchProcessor 82 func ReportError(ctx context.Context, err error, depth int) { 83 // context ctl 84 if errutil.NoReportFromContext(ctx) { 85 return 86 } 87 // global ctl 88 if disableLogErrorReport.Load() { 89 return 90 } 91 // log every time 92 msg := fmt.Sprintf("error: %v", err) 93 sc := trace.SpanFromContext(ctx).SpanContext() 94 if sc.IsEmpty() { 95 logutil.GetErrorLogger().WithOptions(zap.AddCallerSkip(depth)).Error(msg) 96 } else { 97 logutil.GetErrorLogger().WithOptions(zap.AddCallerSkip(depth)).Error(msg, trace.ContextField(ctx)) 98 } 99 // record ctrl 100 if !GetTracerProvider().IsEnable() { 101 return 102 } 103 if ctx == nil { 104 ctx = DefaultContext() 105 } 106 e := &MOErrorHolder{Error: err, Timestamp: time.Now()} 107 GetGlobalBatchProcessor().Collect(ctx, e) 108 }