...
1 package httperr
2
3 import (
4 "fmt"
5 "io"
6 "net/http"
7
8 "github.com/goph/emperror"
9 )
10
11
12 func WithHTTPRequest(err error, r *http.Request) error {
13 return &withHTTPRequest{
14 req: r,
15 err: err,
16 }
17 }
18
19
20
21
22 func HTTPRequest(err error) (*http.Request, bool) {
23 type httpError interface {
24 HTTPRequest() *http.Request
25 }
26
27 var req *http.Request
28
29 emperror.ForEachCause(err, func(err error) bool {
30 if httpErr, ok := err.(httpError); ok {
31 req = httpErr.HTTPRequest()
32
33 return false
34 }
35
36 return true
37 })
38
39 return req, req != nil
40 }
41
42 type withHTTPRequest struct {
43 req *http.Request
44 err error
45 }
46
47 func (w *withHTTPRequest) Error() string {
48 return w.err.Error()
49 }
50
51 func (w *withHTTPRequest) Cause() error {
52 return w.err
53 }
54
55 func (w *withHTTPRequest) HTTPRequest() *http.Request {
56 return w.req
57 }
58
59 func (w *withHTTPRequest) Format(s fmt.State, verb rune) {
60 switch verb {
61 case 'v':
62 if s.Flag('+') {
63 _, _ = fmt.Fprintf(s, "%+v", w.Cause())
64
65 return
66 }
67
68 fallthrough
69
70 case 's':
71 _, _ = io.WriteString(s, w.Error())
72
73 case 'q':
74 _, _ = fmt.Fprintf(s, "%q", w.Error())
75 }
76 }
77
View as plain text