diff --git a/logger.go b/logger.go new file mode 100644 index 0000000..dc0d01f --- /dev/null +++ b/logger.go @@ -0,0 +1,67 @@ +package narco + +import ( + "log" + "os" + "strings" + "time" + + "github.com/codemodus/chain" + "github.com/pivotal-golang/bytefmt" + "golang.org/x/net/context" + + "net/http" +) + +type Logger struct { + //may want a level based logger + *log.Logger +} + +// to make the logger accessible for modification +func NewLogger() *Logger { + return &Logger{log.New(os.Stdout, "[narco] ", 0)} +} + +type FooResponseWriter struct { + header http.Header +} + +func (f *FooResponseWriter) Header() http.Header { + return f.header +} + +func (f *FooResponseWriter) WriteHeader(status int) { +} + +func (f *FooResponseWriter) Write(b []byte) (int, error) { + return len(b), nil +} + +func (l *Logger) Wrap() func(chain.Handler) chain.Handler { + return func(other chain.Handler) chain.Handler { + return chain.HandlerFunc(func(ctx context.Context, h http.ResponseWriter, r *http.Request) { + start := time.Now() + uAgentList, ok := r.Header["User-Agent"] + var uAgent string + if ok == false { + uAgent = "" + } else { + uAgent = strings.Join(uAgentList, "; ") + } + + l.Printf("Requested %s on %s from %s (User-Agent: %s)", r.Method, r.URL.Path, r.RemoteAddr, uAgent) + + //wrap the request with our own interface + hh := WrapResponseWritter(h) + + other.ServeHTTPContext(ctx, hh, r) + + l.Printf("returned %d: %s, size: %s in %s", + hh.Status(), + http.StatusText(hh.Status()), + bytefmt.ByteSize(uint64(hh.Size())), + time.Since(start)) + }) + } +}