package api import ( "encoding/json" "log" "net/http" "path/filepath" "runtime" ) type resp struct { Code int `json:"code"` Msg string `json:"msg"` Data interface{} `json:"data"` TraceID string `json:"trace_id"` } func writeJSON(w http.ResponseWriter, r *http.Request, status int, code int, msg string, data interface{}) { w.Header().Set("Content-Type", "application/json") w.WriteHeader(status) tid := TraceIDFrom(r) b, _ := json.Marshal(resp{Code: code, Msg: msg, Data: data, TraceID: tid}) w.Write(b) if code != 0 { _, file, line, _ := runtime.Caller(1) base := filepath.Base(file) sql := SQLFrom(r) meta := MetaFrom(r) payload := PayloadFrom(r) if sql != "" { log.Printf("trace_id=%s status=%d file=%s:%d method=%s path=%s query=%s remote=%s sql=%s payload=%s msg=%s", tid, status, base, line, meta.Method, meta.Path, meta.Query, meta.Remote, sql, payload, msg) } else { log.Printf("trace_id=%s status=%d file=%s:%d method=%s path=%s query=%s remote=%s payload=%s msg=%s", tid, status, base, line, meta.Method, meta.Path, meta.Query, meta.Remote, payload, msg) } } } func ok(w http.ResponseWriter, r *http.Request, data interface{}) { writeJSON(w, r, http.StatusOK, 0, "ok", data) } func fail(w http.ResponseWriter, r *http.Request, status int, msg string) { writeJSON(w, r, status, 1, msg, nil) } func failCat(w http.ResponseWriter, r *http.Request, status int, msg string, kind string) { writeJSON(w, r, status, 1, msg, nil) tid := TraceIDFrom(r) meta := MetaFrom(r) log.Printf("kind=%s trace_id=%s status=%d method=%s path=%s msg=%s", kind, tid, status, meta.Method, meta.Path, msg) }