github.com/wiselike/revel-cmd@v1.2.1/utils/error.go (about) 1 package utils 2 3 import ( 4 "fmt" 5 "strconv" 6 "strings" 7 ) 8 9 // The error is a wrapper for the. 10 type ( 11 SourceError struct { 12 SourceType string // The type of source that failed to build. 13 Title, Path, Description string // Description of the error, as presented to the user. 14 Line, Column int // Where the error was encountered. 15 SourceLines []string // The entire source file, split into lines. 16 Stack string // The raw stack trace string from debug.Stack(). 17 MetaError string // Error that occurred producing the error page. 18 Link string // A configurable link to wrap the error source in 19 } 20 SourceLine struct { 21 Source string 22 Line int 23 IsError bool 24 } 25 ) 26 27 // Return a new error object. 28 func NewError(source, title, path, description string) *SourceError { 29 return &SourceError{ 30 SourceType: source, 31 Title: title, 32 Path: path, 33 Description: description, 34 } 35 } 36 37 // Creates a link based on the configuration setting "errors.link". 38 func (e *SourceError) SetLink(errorLink string) { 39 errorLink = strings.ReplaceAll(errorLink, "{{Path}}", e.Path) 40 errorLink = strings.ReplaceAll(errorLink, "{{Line}}", strconv.Itoa(e.Line)) 41 42 e.Link = "<a href=" + errorLink + ">" + e.Path + ":" + strconv.Itoa(e.Line) + "</a>" 43 } 44 45 // Error method constructs a plaintext version of the error, taking 46 // account that fields are optionally set. Returns e.g. Compilation Error 47 // (in views/header.html:51): expected right delim in end; got "}". 48 func (e *SourceError) Error() string { 49 if e == nil { 50 panic("opps") 51 } 52 loc := "" 53 if e.Path != "" { 54 line := "" 55 if e.Line != 0 { 56 line = fmt.Sprintf(":%d", e.Line) 57 } 58 loc = fmt.Sprintf("(in %s%s)", e.Path, line) 59 } 60 header := loc 61 if e.Title != "" { 62 if loc != "" { 63 header = fmt.Sprintf("%s %s: ", e.Title, loc) 64 } else { 65 header = fmt.Sprintf("%s: ", e.Title) 66 } 67 } 68 return fmt.Sprintf("%s%s", header, e.Description) 69 } 70 71 // ContextSource method returns a snippet of the source around 72 // where the error occurred. 73 func (e *SourceError) ContextSource() []SourceLine { 74 if e.SourceLines == nil { 75 return nil 76 } 77 start := (e.Line - 1) - 5 78 if start < 0 { 79 start = 0 80 } 81 end := (e.Line - 1) + 5 82 if end > len(e.SourceLines) { 83 end = len(e.SourceLines) 84 } 85 86 lines := make([]SourceLine, end-start) 87 for i, src := range e.SourceLines[start:end] { 88 fileLine := start + i + 1 89 lines[i] = SourceLine{src, fileLine, fileLine == e.Line} 90 } 91 return lines 92 }